Przeglądaj źródła

Merge pull request #1766 from visuddhinanda/laravel

引用书名使用term
visuddhinanda 2 lat temu
rodzic
commit
a2ba1300f7

+ 11 - 7
app/Console/Commands/UpgradeCommunityTerm.php

@@ -18,7 +18,7 @@ class UpgradeCommunityTerm extends Command
      *
      * @var string
      */
-    protected $signature = 'upgrade:community.term {lang}';
+    protected $signature = 'upgrade:community.term {lang} {word?}';
 
     /**
      * The console command description.
@@ -49,22 +49,23 @@ class UpgradeCommunityTerm extends Command
         }
         $lang = strtolower($this->argument('lang'));
         $langFamily = explode('-',$lang)[0];
-        $localTerm = ChannelApi::getSysChannel(
-            "_community_term_{$lang}_"
-        );
+        $localTerm = ChannelApi::getSysChannel("_community_term_{$lang}_");
         if(!$localTerm){
             return 1;
         }
+
         $channelId = ChannelApi::getSysChannel('_System_Pali_VRI_');
         if($channelId === false){
             $this->error('no channel');
             return 1;
         }
-        $table = DhammaTerm::select('word')
+        $table = DhammaTerm::select(['word','tag'])
                             ->whereIn('language',[$this->argument('lang'),$lang,$langFamily])
-                            ->groupBy('word');
-
+                            ->groupBy(['word','tag']);
 
+        if($this->argument('word')){
+            $table = $table->where('word',$this->argument('word'));
+        }
         $words = $table->get();
         $bar = $this->output->createProgressBar(count($words));
         foreach ($words as $key => $word) {
@@ -75,6 +76,7 @@ class UpgradeCommunityTerm extends Command
              */
             $bestNote = "" ;
             $allTerm = DhammaTerm::where('word',$word->word)
+                                ->where('tag',$word->tag)
                                 ->whereIn('language',[$this->argument('lang'),$lang,$langFamily])
                                 ->get();
             $score = [];
@@ -142,6 +144,7 @@ class UpgradeCommunityTerm extends Command
                 $term = DhammaTerm::where('channal',$localTerm)->firstOrNew(
                         [
                             "word" => $word->word,
+                            "tag" => $word->tag,
                             "channal" => $localTerm,
                         ],
                         [
@@ -155,6 +158,7 @@ class UpgradeCommunityTerm extends Command
                             'create_time' => time()*1000,
                         ]
                     );
+                    $term->tag = $word->tag;
                     $term->meaning = $hotMeaning->meaning;
                     $term->note = $bestNote;
                     $term->modify_time = time()*1000;

+ 40 - 80
app/Http/Api/BookTitle.php

@@ -74,46 +74,6 @@ class BookTitle{
     "p_title" => "suttavandanā",
     "abbr" => "suttavandanā"
   ],
-  [
-    "id" => 8,
-    "book" => 5,
-    "name" => "Jinālaṅkāra",
-    "term" => "jinālaṅkāra",
-    "v_title" => "jinālaṅkāra",
-    "m_title" => "jinālaṅkāra",
-    "p_title" => "jinālaṅkāra",
-    "abbr" => "jinālaṅkāra"
-  ],
-  [
-    "id" => 9,
-    "book" => 6,
-    "name" => "Kamalāñjali",
-    "term" => "kamalāñjali",
-    "v_title" => "kamalāñjali",
-    "m_title" => "kamalāñjali",
-    "p_title" => "kamalāñjali",
-    "abbr" => "kamalāñjali"
-  ],
-  [
-    "id" => 10,
-    "book" => 7,
-    "name" => "Pajjamadhu",
-    "term" => "pajjamadhu",
-    "v_title" => "pajjamadhu",
-    "m_title" => "pajjamadhu",
-    "p_title" => "pajjamadhu",
-    "abbr" => "pajjamadhu"
-  ],
-  [
-    "id" => 11,
-    "book" => 8,
-    "name" => "Buddhaguṇagāthāvalī",
-    "term" => "buddhaguṇagāthāvalī",
-    "v_title" => "buddhaguṇagāthāvalī",
-    "m_title" => "buddhaguṇagāthāvalī",
-    "p_title" => "buddhaguṇagāthāvalī",
-    "abbr" => "buddhaguṇagāthāvalī"
-  ],
   [
     "id" => 12,
     "book" => 9,
@@ -587,22 +547,22 @@ class BookTitle{
   [
     "id" => 59,
     "book" => 53,
-    "name" => "Thupavaṃso",
-    "term" => "thupavaṃso",
-    "v_title" => "thupavaṃso",
-    "m_title" => "thupavaṃso",
-    "p_title" => "thupavaṃso",
-    "abbr" => "thupavaṃso"
+    "name" => "Thupavaṃsa",
+    "term" => "thupavaṃsa",
+    "v_title" => "thupavaṃsa",
+    "m_title" => "thupavaṃsa",
+    "p_title" => "thupavaṃsa",
+    "abbr" => "thupavaṃsa"
   ],
   [
     "id" => 60,
     "book" => 54,
-    "name" => "Dāṭhāvaṃso",
-    "term" => "dāṭhāvaṃso",
-    "v_title" => "dāṭhāvaṃso",
-    "m_title" => "dāṭhāvaṃso",
-    "p_title" => "dāṭhāvaṃso",
-    "abbr" => "dāṭhāvaṃso"
+    "name" => "Dāṭhāvaṃsa",
+    "term" => "dāṭhāvaṃsa",
+    "v_title" => "dāṭhāvaṃsa",
+    "m_title" => "dāṭhāvaṃsa",
+    "p_title" => "dāṭhāvaṃsa",
+    "abbr" => "dāṭhāvaṃsa"
   ],
   [
     "id" => 61,
@@ -617,12 +577,12 @@ class BookTitle{
   [
     "id" => 62,
     "book" => 56,
-    "name" => "Dhātuvaṃso",
-    "term" => "dhātuvaṃso",
-    "v_title" => "dhātuvaṃso",
-    "m_title" => "dhātuvaṃso",
-    "p_title" => "dhātuvaṃso",
-    "abbr" => "dhātuvaṃso"
+    "name" => "Dhātuvaṃsa",
+    "term" => "dhātuvaṃsa",
+    "v_title" => "dhātuvaṃsa",
+    "m_title" => "dhātuvaṃsa",
+    "p_title" => "dhātuvaṃsa",
+    "abbr" => "dhātuvaṃsa"
   ],
   [
     "id" => 63,
@@ -2507,31 +2467,31 @@ class BookTitle{
   [
     "id" => 251,
     "book" => 204,
-    "name" => "Sāratthadīpanī-ṭīkā (paṭhamo bhāgo)",
-    "term" => "Sāratthadīpanī-ṭīkā",
-    "v_title" => "Sāratthadīpanī-ṭīkā",
-    "m_title" => "Sāratthadīpanī-ṭīkā",
-    "p_title" => "Sāratthadīpanī-ṭīkā",
+    "name" => "sāratthadīpanī-ṭīkā (paṭhamo bhāgo)",
+    "term" => "sāratthadīpanī-ṭīkā",
+    "v_title" => "sāratthadīpanī-ṭīkā",
+    "m_title" => "sāratthadīpanī-ṭīkā",
+    "p_title" => "sāratthadīpanī-ṭīkā",
     "abbr" => "sārattha. ṭī."
   ],
   [
     "id" => 252,
     "book" => 205,
-    "name" => "Sāratthadīpanī-ṭīkā (dutiyo bhāgo)",
-    "term" => "Sāratthadīpanī-ṭīkā",
-    "v_title" => "Sāratthadīpanī-ṭīkā",
-    "m_title" => "Sāratthadīpanī-ṭīkā",
-    "p_title" => "Sāratthadīpanī-ṭīkā",
+    "name" => "sāratthadīpanī-ṭīkā (dutiyo bhāgo)",
+    "term" => "sāratthadīpanī-ṭīkā",
+    "v_title" => "sāratthadīpanī-ṭīkā",
+    "m_title" => "sāratthadīpanī-ṭīkā",
+    "p_title" => "sāratthadīpanī-ṭīkā",
     "abbr" => "sārattha. ṭī."
   ],
   [
     "id" => 253,
     "book" => 206,
-    "name" => "Sāratthadīpanī-ṭīkā (tatiyo bhāgo)",
-    "term" => "Sāratthadīpanī-ṭīkā",
-    "v_title" => "Sāratthadīpanī-ṭīkā",
-    "m_title" => "Sāratthadīpanī-ṭīkā",
-    "p_title" => "Sāratthadīpanī-ṭīkā",
+    "name" => "sāratthadīpanī-ṭīkā (tatiyo bhāgo)",
+    "term" => "sāratthadīpanī-ṭīkā",
+    "v_title" => "sāratthadīpanī-ṭīkā",
+    "m_title" => "sāratthadīpanī-ṭīkā",
+    "p_title" => "sāratthadīpanī-ṭīkā",
     "abbr" => "sārattha. ṭī."
   ],
   [
@@ -2751,7 +2711,7 @@ class BookTitle{
     "term" => "pārājikapāḷi",
     "v_title" => "pārājikapāḷi",
     "m_title" => "pārājikapāḷi",
-    "p_title" => "vinayapitaka",
+    "p_title" => "vinayapiaka",
     "abbr" => "vi."
   ],
   [
@@ -2761,7 +2721,7 @@ class BookTitle{
     "term" => "pācittiyapāḷi",
     "v_title" => "pācittiyapāḷi",
     "m_title" => "pācittiyapāḷi",
-    "p_title" => "vinayapitaka",
+    "p_title" => "vinayapiaka",
     "abbr" => "vi."
   ],
   [
@@ -2771,7 +2731,7 @@ class BookTitle{
     "term" => "mahāvaggapāḷi",
     "v_title" => "mahāvaggapāḷi",
     "m_title" => "mahāvaggapāḷi",
-    "p_title" => "vinayapitaka",
+    "p_title" => "vinayapiaka",
     "abbr" => "vi."
   ],
   [
@@ -2781,7 +2741,7 @@ class BookTitle{
     "term" => "cūḷavaggapāḷi",
     "v_title" => "cūḷavaggapāḷi",
     "m_title" => "cūḷavaggapāḷi",
-    "p_title" => "vinayapitaka",
+    "p_title" => "vinayapiaka",
     "abbr" => "vi."
   ],
   [
@@ -2791,7 +2751,7 @@ class BookTitle{
     "term" => "parivārapāḷi",
     "v_title" => "parivārapāḷi",
     "m_title" => "parivārapāḷi",
-    "p_title" => "vinayapitaka",
+    "p_title" => "vinayapiaka",
     "abbr" => "vi."
   ],
   [
@@ -2811,10 +2771,10 @@ class BookTitle{
     "term" => "pācittiyapāḷi",
     "v_title" => "pācittiyapāḷi",
     "m_title" => "pācittiyapāḷi",
-    "p_title" => "vinayapitaka",
+    "p_title" => "vinayapiaka",
     "abbr" => "vi."
   ]
-  ];
+];
 
     }
 }

+ 35 - 32
app/Http/Api/TemplateRender.php

@@ -97,7 +97,14 @@ class TemplateRender{
         return $result;
     }
 
-    public function getTermProps($word,$channelId,$channelInfo){
+    public function getTermProps($word,$tag){
+        if(count($this->channel_id)>0){
+            $channelId = $this->channel_id[0];
+        }else{
+            $channelId = null;
+        }
+
+        $channelInfo = $this->channelInfo[0];
         if(Str::isUuid($channelId)){
             $lang = Channel::where('uid',$channelId)->value('lang');
             if(!empty($lang)){
@@ -107,9 +114,12 @@ class TemplateRender{
             }
             $this->info("term:{$word} 先查属于这个channel 的",'term');
             $this->info('channel id'.$channelId,'term');
-            $tplParam = DhammaTerm::where("word",$word)
-                                ->where('channal',$channelId)
-                                ->orderBy('updated_at','desc')
+            $table = DhammaTerm::where("word",$word)
+                                ->where('channal',$channelId);
+            if(!empty($tag)){
+                $table = $table->where('tag',$tag);
+            }
+            $tplParam = $table->orderBy('updated_at','desc')
                                 ->first();
             $studioId = $channelInfo->owner_uid;
         }else{
@@ -128,8 +138,11 @@ class TemplateRender{
              * 语族匹配也行
              */
                 $this->info("没有-再查这个studio的",'term');
-                $termsInStudio = DhammaTerm::where("word",$word)
-                                    ->where('owner',$channelInfo->owner_uid)
+                $table = DhammaTerm::where("word",$word);
+                if(!empty($tag)){
+                    $table = $table->where('tag',$tag);
+                }
+                $termsInStudio = $table->where('owner',$channelInfo->owner_uid)
                                     ->orderBy('updated_at','desc')
                                     ->get();
                 if(count($termsInStudio)>0){
@@ -162,8 +175,11 @@ class TemplateRender{
         if(!$tplParam){
             $this->info("没有,再查社区",'term');
             $community_channel = ChannelApi::getSysChannel("_community_term_zh-hans_");
-            $tplParam = DhammaTerm::where("word",$word)
-                                  ->where('channal',$community_channel)
+            $table = DhammaTerm::where("word",$word);
+            if(!empty($tag)){
+                $table = $table->where('tag',$tag);
+            }
+            $tplParam = $table->where('channal',$community_channel)
                                   ->first();
             if($tplParam){
                 $isCommunity = true;
@@ -195,16 +211,10 @@ class TemplateRender{
 
     private function render_term(){
         $word = $this->get_param($this->param,"word",1);
-        if(count($this->channel_id)>0){
-            $channelId = $this->channel_id[0];
-        }else{
-            $channelId = null;
-        }
 
-        $channelInfo = $this->channelInfo[0];
-        $key = "/term/{$channelId}/{$word}";
-        $props = $this->getTermProps($word,$channelId,$channelInfo);
+        $props = $this->getTermProps($word,'');
 
+        //$key = "/term/{$channelId}/{$word}";
         $output = $props['word'];
         switch ($this->format) {
             case 'react':
@@ -598,24 +608,17 @@ class TemplateRender{
             $props['book'] = $book;
             $props['para'] = $para;
         }
-        //获取原文channel
-        if(isset($this->channelInfo[0])){
-            $lang = $this->channelInfo[0]->lang;
+
+        $term = $this->getTermProps($bookName,':quote:');
+        $props['term'] = $term;
+        if(isset($term['id'])){
+            $props['bookNameLocal'] = $term['meaning'];
+            $text = $term['meaning'];
         }else{
-            $lang = 'en';
-        }
-        if($lang==='zh'){
-            $lang = 'zh-hans';
+            $text = $bookName;
         }
-        $termChannel = ChannelApi::getSysChannel("_System_Grammar_Term_{$lang}_");
-        $bookNameLocal = DhammaTerm::where('channal',$termChannel)
-                ->where('tag',':abbr:')
-                ->where('word',$bookName)
-                ->value('meaning');
-        if($bookNameLocal){
-            $props['bookNameLocal'] = $bookNameLocal;
-        }
-        $text = "{$bookNameLocal}. {$volume}. {$page}";
+        $text .= " {$volume}.{$page}";
+
         switch ($this->format) {
             case 'react':
                 $output = [

+ 0 - 215
app/Http/Controllers/DhammaTermController.php

@@ -404,219 +404,4 @@ class DhammaTermController extends Controller
 		return $this->ok($count);
     }
 
-    public function export(Request $request){
-        $user = AuthApi::current($request);
-        if(!$user){
-            return $this->error(__('auth.failed'));
-        }
-//TODO 判断是否有导出权限
-        switch ($request->get("view")) {
-            case 'channel':
-                # code...
-                $rows = DhammaTerm::where('channal',$request->get("id"))->cursor();
-                break;
-            case 'studio':
-                # code...
-                $studioId = StudioApi::getIdByName($request->get("name"));
-                $rows = DhammaTerm::where('owner',$studioId)->cursor();
-                break;
-            default:
-                $this->error('no view');
-                break;
-        }
-
-        $spreadsheet = new Spreadsheet();
-        $activeWorksheet = $spreadsheet->getActiveSheet();
-        $activeWorksheet->setCellValue('A1', 'id');
-        $activeWorksheet->setCellValue('B1', 'word');
-        $activeWorksheet->setCellValue('C1', 'meaning');
-        $activeWorksheet->setCellValue('D1', 'other_meaning');
-        $activeWorksheet->setCellValue('E1', 'note');
-        $activeWorksheet->setCellValue('F1', 'tag');
-        $activeWorksheet->setCellValue('G1', 'language');
-        $activeWorksheet->setCellValue('H1', 'channel_id');
-
-        $currLine = 2;
-        foreach ($rows as $key => $row) {
-            # code...
-            $activeWorksheet->setCellValue("A{$currLine}", $row->guid);
-            $activeWorksheet->setCellValue("B{$currLine}", $row->word);
-            $activeWorksheet->setCellValue("C{$currLine}", $row->meaning);
-            $activeWorksheet->setCellValue("D{$currLine}", $row->other_meaning);
-            $activeWorksheet->setCellValue("E{$currLine}", $row->note);
-            $activeWorksheet->setCellValue("F{$currLine}", $row->tag);
-            $activeWorksheet->setCellValue("G{$currLine}", $row->language);
-            $activeWorksheet->setCellValue("H{$currLine}", $row->channal);
-            $currLine++;
-        }
-        $writer = new Xlsx($spreadsheet);
-        $fId = Str::uuid();
-        $filename = storage_path("app/tmp/{$fId}");
-        $writer->save($filename);
-        RedisClusters::put("download/tmp/{$fId}",file_get_contents($filename),300);
-        unlink($filename);
-        return $this->ok(['uuid'=>$fId,'filename'=>"term.xlsx",'type'=>"application/vnd.ms-excel"]);
-    }
-
-    public function import(Request $request){
-        $user = AuthApi::current($request);
-        if(!$user){
-            return $this->error(__('auth.failed'));
-        }
-        /**
-         * 判断是否有权限
-         */
-        switch ($request->get('view')) {
-            case 'channel':
-                # 向channel里面导入,忽略源数据的channel id 和 owner 都设置为这个channel 的
-                $channel = ChannelApi::getById($request->get('id'));
-                $owner_id = $channel['studio_id'];
-                if($owner_id !== $user["user_uid"]){
-                    //判断是否为协作
-                    $power = ShareApi::getResPower($user["user_uid"],$request->get('id'));
-                    if($power<20){
-                        return $this->error(__('auth.failed'),[],403);
-                    }
-                }
-                $language = $channel['lang'];
-                break;
-            case 'studio':
-                # 向 studio 里面导入,忽略源数据的 owner 但是要检测 channel id 是否有权限
-                $owner_id = StudioApi::getIdByName($request->get('name'));
-                if(!$owner_id){
-                    return $this->error('no studio name',[],403);
-                }
-
-                break;
-        }
-
-        $message = "";
-        $filename = $request->get('filename');
-        $reader = new \PhpOffice\PhpSpreadsheet\Reader\Xlsx();
-        $reader->setReadDataOnly(true);
-        $spreadsheet = $reader->load($filename);
-        $activeWorksheet = $spreadsheet->getActiveSheet();
-        $currLine = 2;
-        $countFail = 0;
-
-        do {
-            # code...
-            $id = $activeWorksheet->getCell("A{$currLine}")->getValue();
-            $word = $activeWorksheet->getCell("B{$currLine}")->getValue();
-            $meaning = $activeWorksheet->getCell("C{$currLine}")->getValue();
-            $other_meaning = $activeWorksheet->getCell("D{$currLine}")->getValue();
-            $note = $activeWorksheet->getCell("E{$currLine}")->getValue();
-            $tag = $activeWorksheet->getCell("F{$currLine}")->getValue();
-            $language = $activeWorksheet->getCell("G{$currLine}")->getValue();
-            $channel_id = $activeWorksheet->getCell("H{$currLine}")->getValue();
-            $query = ['word'=>$word,'tag'=>$tag];
-            $channelId = null;
-            switch ($request->get('view')) {
-                case 'channel':
-                    # 向channel里面导入,忽略源数据的channel id 和 owner 都设置为这个channel 的
-                    $query['channal'] = $request->get('id');
-                    $channelId = $request->get('id');
-                    break;
-                case 'studio':
-                    # 向 studio 里面导入,忽略源数据的owner 但是要检测 channel id 是否有权限
-                    $query['owner'] = $owner_id;
-                    if(!empty($channel_id)){
-
-                        //有channel 数据,查看是否在studio中
-                        $channel = ChannelApi::getById($channel_id);
-                        if($channel === false){
-                            $message .= "没有查到版本信息:{$channel_id} - {$word}\n";
-                            $currLine++;
-                            $countFail++;
-                            continue 2;
-                        }
-                        if($owner_id != $channel['studio_id']){
-                            $message .= "版本不在studio中:{$channel_id} - {$word}\n";
-                            $currLine++;
-                            $countFail++;
-                            continue 2;
-                        }
-                        $query['channal'] = $channel_id;
-                        $channelId = $channel_id;
-                    }
-                    # code...
-                    break;
-            }
-
-            if(empty($id) && empty($word)){
-                break;
-            }
-
-            //查询此id是否有旧数据
-            if(!empty($id)){
-                $oldRow = DhammaTerm::find($id);
-                //TODO 有 id 无 word 删除数据
-                if(empty($word)){
-                    //查看权限
-                    if($oldRow->owner !== $user['user_uid']){
-                        if(!empty($oldRow->channal)){
-                            //看是否为协作
-                            $power = ShareApi::getResPower($user['user_uid'],$oldRow->channal);
-                            if($power < 20){
-                                $message .= "无删除权限:{$id} - {$word}\n";
-                                $currLine++;
-                                $countFail++;
-                                continue;
-                            }
-                        }else{
-                            $message .= "无删除权限:{$id} - {$word}\n";
-                            $currLine++;
-                            $countFail++;
-                            continue;
-                        }
-                    }
-                    //删除
-                    $oldRow->delete();
-                    $currLine++;
-                    continue;
-                }
-            }else{
-                $oldRow = null;
-            }
-            //查询是否跟已有数据重复
-            $row = DhammaTerm::where($query)->first();
-            if(!$row){
-                //不重复
-                if(isset($oldRow) && $oldRow){
-                    //找到旧的记录-修改旧数据
-                    $row = $oldRow;
-                }else{
-                    //没找到旧的记录-新建
-                    $row = new DhammaTerm();
-                    $row->id = app('snowflake')->id();
-                    $row->guid = Str::uuid();
-                    $row->word = $word;
-                    $row->create_time = time()*1000;
-                }
-            }else{
-                //重复-如果与旧的id不同,报错
-                if(isset($oldRow) && $oldRow && $row->guid !== $id){
-                    $message .= "重复的数据:{$id} - {$word}\n";
-                    $currLine++;
-                    $countFail++;
-                    continue;
-                }
-            }
-            $row->word = $word;
-            $row->word_en = Tools::getWordEn($word);
-            $row->meaning = $meaning;
-            $row->other_meaning = $other_meaning;
-            $row->note = $note;
-            $row->tag = $tag;
-            $row->language = $language;
-            $row->channal = $channelId;
-            $row->editor_id = $user['user_id'];
-            $row->owner = $owner_id;
-            $row->modify_time = time()*1000;
-            $row->save();
-
-            $currLine++;
-        } while (true);
-        return $this->ok(["success"=>$currLine-2-$countFail,'fail'=>($countFail)],$message);
-    }
 }

+ 2 - 2
app/Http/Controllers/PageIndexController.php

@@ -65,9 +65,9 @@ class PageIndexController extends Controller
             ],
             [
                 'image'=>'/assets/gallery/04.jpg',
-                'title'=>'云台翻译中心',
+                'title'=>'翻译中心接待室',
                 'id'=>'desc_04',
-                'description'=>'外景',
+                'description'=>'人工湖畔的接待室,访客活动中心',
             ],
             [
                 'image'=>'/assets/gallery/05.jpg',

+ 304 - 0
app/Http/Controllers/TermExportController.php

@@ -0,0 +1,304 @@
+<?php
+
+namespace App\Http\Controllers;
+
+use App\Models\DhammaTerm;
+use Illuminate\Http\Request;
+use Illuminate\Support\Facades\Redis;
+use Illuminate\Support\Facades\Storage;
+use Illuminate\Support\Str;
+use PhpOffice\PhpSpreadsheet\Spreadsheet;
+use PhpOffice\PhpSpreadsheet\Writer\Xlsx;
+
+use App\Http\Api\AuthApi;
+use App\Http\Api\StudioApi;
+use App\Http\Api\ChannelApi;
+use App\Http\Api\ShareApi;
+use App\Tools\Tools;
+
+class TermExportController extends Controller
+{
+    /**
+     * Display a listing of the resource.
+     *
+     * @return \Illuminate\Http\Response
+     */
+    public function index(Request $request)
+    {
+        $user = AuthApi::current($request);
+        if(!$user){
+            return $this->error(__('auth.failed'));
+        }
+//TODO 判断是否有导出权限
+        switch ($request->get("view")) {
+            case 'channel':
+                # code...
+                $rows = DhammaTerm::where('channal',$request->get("id"))->cursor();
+                break;
+            case 'studio':
+                # code...
+                $studioId = StudioApi::getIdByName($request->get("name"));
+                $rows = DhammaTerm::where('owner',$studioId)->cursor();
+                break;
+            default:
+                $this->error('no view');
+                break;
+        }
+
+        $spreadsheet = new Spreadsheet();
+        $activeWorksheet = $spreadsheet->getActiveSheet();
+        $activeWorksheet->setCellValue('A1', 'id');
+        $activeWorksheet->setCellValue('B1', 'word');
+        $activeWorksheet->setCellValue('C1', 'meaning');
+        $activeWorksheet->setCellValue('D1', 'other_meaning');
+        $activeWorksheet->setCellValue('E1', 'note');
+        $activeWorksheet->setCellValue('F1', 'tag');
+        $activeWorksheet->setCellValue('G1', 'language');
+        $activeWorksheet->setCellValue('H1', 'channel_id');
+
+        $currLine = 2;
+        foreach ($rows as $key => $row) {
+            # code...
+            $activeWorksheet->setCellValue("A{$currLine}", $row->guid);
+            $activeWorksheet->setCellValue("B{$currLine}", $row->word);
+            $activeWorksheet->setCellValue("C{$currLine}", $row->meaning);
+            $activeWorksheet->setCellValue("D{$currLine}", $row->other_meaning);
+            $activeWorksheet->setCellValue("E{$currLine}", $row->note);
+            $activeWorksheet->setCellValue("F{$currLine}", $row->tag);
+            $activeWorksheet->setCellValue("G{$currLine}", $row->language);
+            $activeWorksheet->setCellValue("H{$currLine}", $row->channal);
+            $currLine++;
+        }
+        $writer = new Xlsx($spreadsheet);
+        $fId = Str::uuid();
+        $filename = storage_path("app/tmp/{$fId}");
+        $writer->save($filename);
+        $key = "download/tmp/{$fId}";
+        Redis::set($key,file_get_contents($filename));
+        Redis::expire($key,300);
+        unlink($filename);
+        return $this->ok(['uuid'=>$fId,'filename'=>"term.xlsx",'type'=>"application/vnd.ms-excel"]);
+    }
+
+    /**
+     * Store a newly created resource in storage.
+     *
+     * @param  \Illuminate\Http\Request  $request
+     * @return \Illuminate\Http\Response
+     */
+    public function store(Request $request)
+    {
+        //
+    }
+
+    /**
+     * Display the specified resource.
+     *
+     * @param  string  $downloadId
+     * @return \Illuminate\Http\Response
+     */
+    public function show(string $downloadId)
+    {
+        header('Content-Type: application/vnd.ms-excel');
+        header('Content-Disposition: attachment; filename="term.xlsx"');
+        $content = Redis::get("download/tmp/{$downloadId}");
+        file_put_contents("php://output",$content);
+    }
+
+    public function import(Request $request){
+        $user = AuthApi::current($request);
+        if(!$user){
+            return $this->error(__('auth.failed'),401,401);
+        }
+        /**
+         * 判断是否有权限
+         */
+        switch ($request->get('view')) {
+            case 'channel':
+                # 向channel里面导入,忽略源数据的channel id 和 owner 都设置为这个channel 的
+                $channel = ChannelApi::getById($request->get('id'));
+                $owner_id = $channel['studio_id'];
+                if($owner_id !== $user["user_uid"]){
+                    //判断是否为协作
+                    $power = ShareApi::getResPower($user["user_uid"],$request->get('id'));
+                    if($power<20){
+                        return $this->error(__('auth.failed'),403,403);
+                    }
+                }
+                $language = $channel['lang'];
+                break;
+            case 'studio':
+                # 向 studio 里面导入,忽略源数据的 owner 但是要检测 channel id 是否有权限
+                $owner_id = StudioApi::getIdByName($request->get('name'));
+                if(!$owner_id){
+                    return $this->error('no studio name',403,403);
+                }
+
+                break;
+        }
+
+        $message = "";
+        $filename = $request->get('filename');
+        if(Storage::missing($filename)){
+            return $this->error('no file '.$filename);
+        }
+        $contents = Storage::get($filename);
+        $fId = Str::uuid();
+        $tmpFile = storage_path("app/tmp/{$fId}.xlsx");
+        $ok = file_put_contents($tmpFile,$contents);
+        if($ok===false){
+            return $this->error('create tmp file fail '.$tmpFile,500,500);
+        }
+        $reader = new \PhpOffice\PhpSpreadsheet\Reader\Xlsx();
+        $reader->setReadDataOnly(true);
+        $spreadsheet = $reader->load($tmpFile);
+        $activeWorksheet = $spreadsheet->getActiveSheet();
+        $currLine = 2;
+        $countFail = 0;
+
+        do {
+            # code...
+            $id = $activeWorksheet->getCell("A{$currLine}")->getValue();
+            $word = $activeWorksheet->getCell("B{$currLine}")->getValue();
+            $meaning = $activeWorksheet->getCell("C{$currLine}")->getValue();
+            $other_meaning = $activeWorksheet->getCell("D{$currLine}")->getValue();
+            $note = $activeWorksheet->getCell("E{$currLine}")->getValue();
+            $tag = $activeWorksheet->getCell("F{$currLine}")->getValue();
+            $language = $activeWorksheet->getCell("G{$currLine}")->getValue();
+            $channel_id = $activeWorksheet->getCell("H{$currLine}")->getValue();
+            $query = ['word'=>$word,'tag'=>$tag];
+            $channelId = null;
+            switch ($request->get('view')) {
+                case 'channel':
+                    # 向channel里面导入,忽略源数据的channel id 和 owner 都设置为这个channel 的
+                    $query['channal'] = $request->get('id');
+                    $channelId = $request->get('id');
+                    break;
+                case 'studio':
+                    # 向 studio 里面导入,忽略源数据的owner 但是要检测 channel id 是否有权限
+                    $query['owner'] = $owner_id;
+                    if(!empty($channel_id)){
+
+                        //有channel 数据,查看是否在studio中
+                        $channel = ChannelApi::getById($channel_id);
+                        if($channel === false){
+                            $message .= "没有查到版本信息:{$channel_id} - {$word}\n";
+                            $currLine++;
+                            $countFail++;
+                            continue 2;
+                        }
+                        if($owner_id != $channel['studio_id']){
+                            $message .= "版本不在studio中:{$channel_id} - {$word}\n";
+                            $currLine++;
+                            $countFail++;
+                            continue 2;
+                        }
+                        $query['channal'] = $channel_id;
+                        $channelId = $channel_id;
+                    }
+                    # code...
+                    break;
+            }
+
+            if(empty($id) && empty($word)){
+                break;
+            }
+
+            //查询此id是否有旧数据
+            if(!empty($id)){
+                $oldRow = DhammaTerm::find($id);
+                //TODO 有 id 无 word 删除数据
+                if(empty($word)){
+                    //查看权限
+                    if($oldRow->owner !== $user['user_uid']){
+                        if(!empty($oldRow->channal)){
+                            //看是否为协作
+                            $power = ShareApi::getResPower($user['user_uid'],$oldRow->channal);
+                            if($power < 20){
+                                $message .= "无删除权限:{$id} - {$word}\n";
+                                $currLine++;
+                                $countFail++;
+                                continue;
+                            }
+                        }else{
+                            $message .= "无删除权限:{$id} - {$word}\n";
+                            $currLine++;
+                            $countFail++;
+                            continue;
+                        }
+                    }
+                    //删除
+                    $oldRow->delete();
+                    $currLine++;
+                    continue;
+                }
+            }else{
+                $oldRow = null;
+            }
+            //查询是否跟已有数据重复
+            $row = DhammaTerm::where($query)->first();
+            if(!$row){
+                //不重复
+                if(isset($oldRow) && $oldRow){
+                    //找到旧的记录-修改旧数据
+                    $row = $oldRow;
+                }else{
+                    //没找到旧的记录-新建
+                    $row = new DhammaTerm();
+                    $row->id = app('snowflake')->id();
+                    $row->guid = Str::uuid();
+                    $row->word = $word;
+                    $row->create_time = time()*1000;
+                }
+            }else{
+                //重复-如果与旧的id不同,报错
+                if(isset($oldRow) && $oldRow && $row->guid !== $id){
+                    $message .= "重复的数据:{$id} - {$word}\n";
+                    $currLine++;
+                    $countFail++;
+                    continue;
+                }
+            }
+            $row->word = $word;
+            $row->word_en = Tools::getWordEn($word);
+            $row->meaning = $meaning;
+            $row->other_meaning = $other_meaning;
+            $row->note = $note;
+            $row->tag = $tag;
+            $row->language = $language;
+            $row->channal = $channelId;
+            $row->editor_id = $user['user_id'];
+            $row->owner = $owner_id;
+            $row->modify_time = time()*1000;
+            $row->save();
+
+            $currLine++;
+        } while (true);
+        unlink($tmpFile);
+        return $this->ok(["success"=>$currLine-2-$countFail,'fail'=>($countFail)],$message);
+    }
+
+
+    /**
+     * Update the specified resource in storage.
+     *
+     * @param  \Illuminate\Http\Request  $request
+     * @param  \App\Models\DhammaTerm  $dhammaTerm
+     * @return \Illuminate\Http\Response
+     */
+    public function update(Request $request, DhammaTerm $dhammaTerm)
+    {
+        //
+    }
+
+    /**
+     * Remove the specified resource from storage.
+     *
+     * @param  \App\Models\DhammaTerm  $dhammaTerm
+     * @return \Illuminate\Http\Response
+     */
+    public function destroy(DhammaTerm $dhammaTerm)
+    {
+        //
+    }
+}

+ 9 - 3
app/Http/Controllers/UploadController.php

@@ -33,11 +33,17 @@ class UploadController extends Controller
         $file = $request->file('file');
 
        //Move Uploaded File
-        $bucket = date("Y-m-d");
-        $filename = $file->store('tmp/'.date("Y-m-d"),'local');
+       if($request->get('is_tmp',false) == false){
+        $bucket = config('mint.attachments.bucket_name.permanent');
+       }else{
+        $bucket = config('mint.attachments.bucket_name.temporary');
+       }
+
+       $uploadFilename = Str::uuid().'.'.$file->extension();
+        $filename = $file->storeAs($bucket,$uploadFilename);
 
         $json = array(
-            'name' => $filename,
+            'filename' => $bucket.'/'.$uploadFilename,
             'size' => $file->getSize(),
             'type' => $file->getMimeType(),
             'url' => storage_path('app/'.$filename),

BIN
public/assets/gallery/05.jpg


+ 4 - 2
routes/api.php

@@ -79,6 +79,7 @@ use App\Http\Controllers\SearchPageNumberController;
 use App\Http\Controllers\NavPageController;
 use App\Http\Controllers\BookTitleController;
 use App\Http\Controllers\SystemTermController;
+use App\Http\Controllers\TermExportController;
 
 /*
 |--------------------------------------------------------------------------
@@ -97,9 +98,10 @@ Route::middleware('auth:sanctum')->get('/user', function (Request $request) {
 
 Route::group(['prefix' => 'v2'],function(){
 	Route::apiResource('wbw_templates',WbwTemplateController::class);
+
 	Route::apiResource('terms',DhammaTermController::class);
-	Route::get('terms-export',[DhammaTermController::class,"export"]);
-    Route::get('terms-import',[DhammaTermController::class,"import"]);
+	Route::apiResource('terms-export',TermExportController::class);
+	Route::get('terms-import',[TermExportController::class,'import']);
     Route::get('system-term/{lang}/{word}',[SystemTermController::class,"show"]);
 
 	Route::apiResource('sentence',SentenceController::class);