Browse Source

兼容avss的多语言录入下载

tanghongbin 5 years ago
parent
commit
01b8239b28

+ 241 - 0
controller/LangAVSSController.py

@@ -0,0 +1,241 @@
+#!/usr/bin/env python3
+# -*- coding: utf-8 -*-
+import json
+import time
+from tokenize import Token
+
+from django.views.generic.base import TemplateView
+
+from model.models import LangClassModel, LangKeyModel, LangAreaModel, LangValModel, LangKeyClassModel, \
+    LangLocationModel, UserModel
+from object.ResponseObject import ResponseObject
+from object.TokenObject import TokenObject
+
+
+class LangAVSSView(TemplateView):
+    def post(self, request, *args, **kwargs):
+        request.encoding = 'utf-8'
+        operation = kwargs.get('operation', None)
+        request_dict = json.loads(request.body.decode('utf-8'))
+        return self.validate(request_dict, operation)
+
+    def get(self, request, *args, **kwargs):
+        request.encoding = 'utf-8'
+        request_dict = request.GET
+        operation = kwargs.get('operation', None)
+        return self.validate(request_dict, operation)
+
+    def validate(self, request_dict, operation):
+        response = ResponseObject()
+        if operation == 'add':
+            return self.do_add(request_dict, response)
+        elif operation == 'delete':
+            return self.do_delete(request_dict, response)
+        elif operation == 'add_single':
+            return self.do_add_single(request_dict, response)
+        else:
+            return response.json(404)
+
+    def do_add(self, request_dict, response):
+        data = request_dict.get('data', None)
+        print(data)
+        if data:
+            data = json.loads(data)
+            keys = data.keys()
+            for key in keys:
+                # 取出模块,每个context
+                langClass = data[key]
+                # print(langClass['name'])
+
+                lc_qs = LangClassModel.objects.filter(name=key)
+                if not lc_qs.exists():
+                    LangClassModel.objects.create(**{'name': key})
+
+                langClassModel = LangClassModel.objects.get(name=key)
+
+                # 每个context里面的语言
+                languages = langClass['languages']
+                # print(languages)
+                langKeys = languages.keys()
+                for langKey in langKeys:
+                    # print(langKey)
+
+                    # 取出每个语言
+                    language = languages[langKey]
+                    # print(language)
+                    lk_qs = LangKeyModel.objects.filter(word_key=langKey)
+                    lkModel = None
+                    if lk_qs.exists():
+                        lkModel = lk_qs[0]
+                        lkModel.type = 2
+                        lkModel.save()
+
+                    else:
+                        # 插入新的key
+                        addTime = int(time.time())
+                        lk = {
+                            'word_key': language['source'],
+                            'addTime': addTime,
+                            'updTime': addTime,
+                            'type': 1,
+                        }
+                        lkModel = LangKeyModel.objects.create(**lk)
+                        # lkModel = lkModel[0]
+                        translations = language['translation']
+                        for translation in translations:
+                            la_id = translation['la_id']
+                            val = translation['val']
+                            langArea = LangAreaModel.objects.filter(id=la_id)[0]
+                            # 插入key对应的value
+                            # 插入新的key
+                            addTime = int(time.time())
+                            langValue = {
+                                'lk': lkModel,
+                                'la': langArea,
+                                'word_val': val,
+                                'addTime': addTime,
+                                'updTime': addTime,
+                                'status': 1
+                            }
+                            LangValModel.objects.create(**langValue)
+
+                    # 语言的key
+                    # print('source = ' + language['source'])
+                    # 语言的value
+                    # print('translation = ' + language['translation'])
+
+                    lkc_qs = LangKeyClassModel.objects.filter(lk__id=lkModel.id, clazz__id=langClassModel.id)
+                    if not lkc_qs.exists():
+                        # 创建langClass和langKey的映射关系
+                        langKeyClass = {
+                            'lk': lkModel,
+                            'clazz': langClassModel
+                        }
+                        LangKeyClassModel.objects.create(**langKeyClass)
+
+                        # 语言的在代码中的位置
+                        locations = language['locations']
+                        for location in locations:
+                            # print(location['filename'])
+                            # print(location['line'])
+
+                            locationValue = {
+                                'lk': lkModel,
+                                'filename': location['filename'],
+                                'line': location['line']
+                            }
+                            LangLocationModel.objects.create(**locationValue)
+            return response.json(0)
+        else:
+            return response.json(444)
+
+    def do_add_single(self, request_dict, response):
+        word_class = request_dict.get('word_class', None)
+        word_key = request_dict.get('word_key', None)
+        word_array = request_dict.get('word_array', None)
+        location_array = request_dict.get('location_array', None)
+
+        if word_class and word_key and word_array and location_array:
+            # 判断lang_class是否存在
+            lc_qs = LangClassModel.objects.filter(name=word_class)
+            if not lc_qs.exists():
+                LangClassModel.objects.create(**{'name': word_class})
+
+            langClassModel = LangClassModel.objects.get(name=word_class)
+
+            # 取出每个语言
+            lk_qs = LangKeyModel.objects.filter(word_key=word_key)
+            lkModel = None
+            if lk_qs.exists():
+                lkModel = lk_qs[0]
+                if lkModel.type == 0:
+                    lkModel.type = 2
+                    lkModel.save()
+
+            else:
+                # 插入新的key
+                addTime = int(time.time())
+                lk = {
+                    'word_key': word_key,
+                    'addTime': addTime,
+                    'updTime': addTime,
+                    'type': 1,
+                }
+                lkModel = LangKeyModel.objects.create(**lk)
+                # lkModel = lkModel[0]
+                translations = list(word_array)
+                for translation in translations:
+                    la_id = translation['la_id']
+                    val = translation['val']
+                    langArea = LangAreaModel.objects.filter(id=la_id)[0]
+                    # 插入key对应的value
+                    # 插入新的key
+                    addTime = int(time.time())
+                    langValue = {
+                        'lk': lkModel,
+                        'la': langArea,
+                        'word_val': val,
+                        'addTime': addTime,
+                        'updTime': addTime,
+                        'status': 1
+                    }
+                    LangValModel.objects.create(**langValue)
+
+            lkc_qs = LangKeyClassModel.objects.filter(lk__id=lkModel.id, clazz__id=langClassModel.id)
+            if not lkc_qs.exists():
+                # 创建langClass和langKey的映射关系
+                langKeyClass = {
+                    'lk': lkModel,
+                    'clazz': langClassModel
+                }
+                LangKeyClassModel.objects.create(**langKeyClass)
+
+                # 语言的在代码中的位置
+                locations = list(location_array)
+                for location in locations:
+                    # print(location['filename'])
+                    # print(location['line'])
+
+                    locationValue = {
+                        'lk': lkModel,
+                        'filename': location['filename'],
+                        'line': location['line']
+                    }
+                    LangLocationModel.objects.create(**locationValue)
+            return response.json(0)
+        else:
+            return response.json(444)
+
+    def do_delete(self, request_dict, response):
+        word_key = request_dict.get('word_key', None)
+        token = request_dict.get('token', None)
+
+        response = ResponseObject()
+
+        token = TokenObject(token)
+        if token.code != 0:
+            return response.json(token.code)
+
+        user_qs = UserModel.objects.filter(id=token.userID, username='admin')
+        if not user_qs.exists():
+            return response.json(403)
+
+        if word_key:
+            try:
+                lk_qs = LangKeyModel.objects.filter(word_key=word_key)
+                if lk_qs.exists():
+                    lk = lk_qs[0]
+                    if lk.type == 2:
+                        lk.type = 0
+                        lk.save()
+                    else:
+                        lk_qs.delete()
+                        LangValModel.objects.filter(lk__word_key=word_key).delete()
+                LangLocationModel.objects.filter(lk__word_key=word_key).delete()
+                LangKeyClassModel.objects.filter(lk__word_key=word_key).delete()
+            except Exception as e:
+                return response.json(404, repr(e))
+            else:
+                return response.json(0)
+        else:
+            return response.json(444)

+ 69 - 4
controller/LangArea.py

@@ -20,7 +20,7 @@ from django.views.decorators.csrf import csrf_exempt
 from django.utils.decorators import method_decorator
 from object.ResponseObject import ResponseObject
 from django.contrib.auth.hashers import make_password, check_password
-from model.models import UserModel, LangSetModel, LangAreaModel, LangValModel, LangKeyModel
+from model.models import UserModel, LangSetModel, LangAreaModel, LangValModel, LangKeyModel, LangKeyClassModel
 import time
 from object.TokenObject import TokenObject
 from django.http import StreamingHttpResponse
@@ -117,14 +117,19 @@ class LangAreaView(TemplateView):
         id = request_dict.get('id', None)
         type = request_dict.get('type', None)
         # key_list = LangKeyModel.objects.filter().values_list('word_key', flat=True)
-        en_qs = LangKeyModel.objects.filter(langvalmodel__la__id=20).values('word_key', 'langvalmodel__word_val')
+        print('id = ' + id)
+        langType = (0, 2)
+        if type == 'avss':
+            langType = (1, 2)
+
+        en_qs = LangKeyModel.objects.filter(langvalmodel__la__id=20, type__in=langType).values('word_key', 'langvalmodel__word_val')
         en_kv = {}
         for e in en_qs:
             en_kv[e['word_key']] = e['langvalmodel__word_val']
 
         content = ''
         if type == 'ios':
-            res_qs = LangKeyModel.objects.filter(langvalmodel__la__id=id).\
+            res_qs = LangKeyModel.objects.filter(langvalmodel__la__id=id, type__in=langType).\
                 values('word_key', 'langvalmodel__word_val')
             res = {}
             for r in res_qs:
@@ -137,7 +142,7 @@ class LangAreaView(TemplateView):
                 content_val = res[l].replace('"', '\'')
                 content = content + '"' + l + '"="' + content_val + '";\n'
         elif type == 'android':
-            res_qs = LangKeyModel.objects.filter(langvalmodel__la__id=id).\
+            res_qs = LangKeyModel.objects.filter(langvalmodel__la__id=id, type__in=langType).\
                 values('word_key', 'langvalmodel__word_val').order_by('addTime')
             res = {}
             for r in res_qs:
@@ -175,12 +180,72 @@ class LangAreaView(TemplateView):
                 content_val = res[l].replace("'", "\\'")
                 content_val = content_val.replace('"', '\\"')
                 content = content + '<string name="' + lk + '">' + content_val + '</string>\n'
+        elif type == 'avss':
+            content = self.do_download_avss(id)
         response = StreamingHttpResponse(content)
         response['Content-Type'] = 'application/octet-stream'
         response['Content-Disposition'] = 'attachment;filename="lang.txt"'
         return response
         return response.json(0, res)
 
+    def do_download_avss(self, id):
+        content = ''
+        result = {}
+        lkc_qs = LangKeyModel.objects.filter(langvalmodel__la__id=id, type__in=(1, 2)).values('word_key', 'langkeyclassmodel__clazz__name', 'langvalmodel__word_val', 'langlocationmodel__filename', 'langlocationmodel__line')
+        if lkc_qs.exists():
+            for lkc in lkc_qs:
+                # print(lkc)
+                name = lkc['langkeyclassmodel__clazz__name']
+                hasClass = result.__contains__(name)
+                if hasClass is False:
+                    result[name] = {}
+
+                source = lkc['word_key']
+                if not result[name].__contains__(source):
+                    result[name][source] = {}
+                message = result[name][source]
+
+                message['source'] = source
+                message['translation'] = lkc['langvalmodel__word_val']
+
+                # location
+                locations = []
+                locations.append({'filename': lkc['langlocationmodel__filename'], 'line': lkc['langlocationmodel__line']})
+                message['locations'] = locations
+            print(result)
+
+            content += '<TS>\n'
+            keys = result.keys()
+            for key in keys:
+                content += '<context>\n<name>'
+                content += key
+                content += '</name>\n'
+
+                messages = result[key]
+                messageKeys = messages.keys()
+                for messageKey in messageKeys:
+                    message = messages[messageKey]
+                    content += '<message>\n'
+                    content += '<source>'
+                    content += message['source']
+                    content += '</source>\n'
+                    content += '<translation>'
+                    content += message['translation']
+                    content += '</translation>\n'
+
+                    locations = message['locations']
+                    print(message)
+                    for location in locations:
+                        if location['filename'] != '':
+                            content += '<location filename=\"' + location['filename'] + '\" line=\"' + str(location['line']) + '\"\n/>'
+                    content += '</message>\n'
+                content += '</TS>'
+            return content
+        else:
+            print('none')
+
+        return content
+
 
 from django.http import StreamingHttpResponse
 

+ 24 - 6
controller/LangWord.py

@@ -122,7 +122,7 @@ class LangWordView(TemplateView):
                     lk.update(word_key=word_key, updTime=nowTime)
             else:
                 lk.update(updTime=nowTime)
-            #如果是管理员,是status的值为1,表示记录为新增
+            # 如果是管理员,是status的值为1,表示记录为新增
             user = UserModel.objects.get(id=userID)
             lang_perm_ql = LangPermModel.objects.filter(user__id=userID).values_list('lang__lang', flat=True)
             lang_perm_ls = list(lang_perm_ql)
@@ -150,18 +150,27 @@ class LangWordView(TemplateView):
             return response.json(403)
         word_key = request_dict.get('word_key', None)
         try:
-            LangKeyModel.objects.filter(word_key=word_key).delete()
-            LangValModel.objects.filter(lk__word_key=word_key).delete()
+            lk_qs = LangKeyModel.objects.filter(word_key=word_key)
+            if lk_qs.exists():
+                lk = lk_qs[0]
+                if lk.type == 2:
+                    lk.type = 1
+                    lk.save()
+                else:
+                    lk_qs.delete()
+                    LangValModel.objects.filter(lk__word_key=word_key).delete()
         except Exception as e:
             return response.json(404, repr(e))
         else:
             return response.json(0)
 
     def do_query(self, request_dict, response, userID):
+        print(request_dict)
         page = int(request_dict.get('page', None))
         line = int(request_dict.get('line', None))
         searchKey = request_dict.get('searchKey', None)
         searchVal = request_dict.get('searchVal', None)
+        langType = request_dict.get('langType', None)
         if searchKey:
             searchKey = searchKey.strip()
         if searchVal:
@@ -171,13 +180,22 @@ class LangWordView(TemplateView):
             lang_set_list = LangSetModel.objects.filter(user__id=userID).values_list('lang__id', flat=True)
             lang_set_list = list(lang_set_list)
             la_qs = LangAreaModel.objects.filter(id__in=lang_set_list).values('lang', 'id')
-            lk_qs = LangKeyModel.objects.filter()
+
+            type_value = (0, 2)
+            print(langType)
+            if langType:
+                tmpType = int(langType)
+                print(tmpType)
+                if tmpType == 1:
+                    type_value = (1, 2)
+
+            lk_qs = LangKeyModel.objects.filter(type__in=type_value)
             if searchKey and searchVal:
                 if searchKey == 'key':
-                    lk_qs = lk_qs.filter(word_key__contains=searchVal)
+                    lk_qs = lk_qs.filter(word_key__contains=searchVal, type__in=type_value)
                     # lk_qs = lk_qs.filter(word_key=searchVal)
                 else:
-                    lk_qs = lk_qs.filter(langvalmodel__word_val__contains=searchVal, langvalmodel__la__lang=searchKey)
+                    lk_qs = lk_qs.filter(langvalmodel__word_val__contains=searchVal, langvalmodel__la__lang=searchKey, type__in=type_value)
             count = lk_qs.count()
             # lk_qs = lk_qs[(page - 1) * line:page * line].values_list('word_key', flat=True)
             if orderByupdate == 1:

+ 49 - 0
langer/languageparse.py

@@ -0,0 +1,49 @@
+#!/usr/bin/env python3
+# -*- coding: utf-8 -*-
+import json
+import requests
+
+
+from object.LanguageParser import LanguageParser
+
+if __name__ == "__main__":
+
+    parser = LanguageParser()
+    enResult = parser.parser("./file/app_en_US.ts")
+    cnResult = parser.parser("./file/app_zh_CN.ts")
+    # print(cnResult)
+
+    classKeys = enResult.keys()
+    data = {}
+    postData = {}
+    url = 'http://192.168.136.35:8800/avss/add_single'
+    for classKey in classKeys:
+        classMap = {}
+        data[classKey] = classMap
+        classMap['name'] = classKey
+
+        # 取出languages
+        languageMap = {}
+        languages = enResult[classKey]['languages']
+        langKeys = languages.keys()
+        for langKey in langKeys:
+            language = languages[langKey]
+            translation = []
+            translation.append({'la_id': 20, 'val': language['translation']})
+            translation.append({'la_id': 18, 'val': cnResult[classKey]['languages'][langKey]['translation']})
+
+            language['translation'] = translation
+            languageMap[langKey] = language
+
+            postData['word_class'] = classKey
+            postData['word_key'] = langKey
+            postData['word_array'] = translation
+            postData['location_array'] = language['locations']
+
+            res = requests.post(url=url, data=json.dumps(postData))
+            print(res)
+        classMap['languages'] = languageMap
+    print(data)
+
+
+

+ 3 - 1
langer/urls.py

@@ -1,6 +1,7 @@
 from django.contrib import admin
 from django.urls import path, re_path
-from controller import User, LangSet, LangWord, LangArea, WebHook, AsImg, SysSet, Lottery, SkuSuitName,SkuConditionName,SkuRuleName,EmailSend
+from controller import User, LangSet, LangWord, LangArea, WebHook, AsImg, SysSet, Lottery, SkuSuitName, \
+    SkuConditionName, SkuRuleName, EmailSend, LangAVSSController
 
 urlpatterns = [
     path('admin/', admin.site.urls),
@@ -39,5 +40,6 @@ urlpatterns = [
     re_path('sku_condition/(?P<operation>.*)', SkuConditionName.skuConditionView.as_view()),
     re_path('cku_rule/(?P<operation>.*)', SkuRuleName.skuRuleView.as_view()),
     re_path('email_send/(?P<operation>.*)', EmailSend.EmailSendView.as_view()),
+    re_path('avss/(?P<operation>.*)', LangAVSSController.LangAVSSView.as_view()),
 
 ]

+ 35 - 1
model/models.py

@@ -54,6 +54,7 @@ class LangKeyModel(models.Model):
     word_key = models.CharField(default='', max_length=64, verbose_name='词汇键', unique=True)
     addTime = models.IntegerField(default=0, verbose_name='添加时间')
     updTime = models.IntegerField(default=0, verbose_name='更新时间')
+    type = models.SmallIntegerField(default=0, verbose_name='词汇键类型')  # 0:移动端;1:pc端(avss);2:两端共同拥有
 
     class Meta:
         ordering = ('-addTime',)
@@ -169,4 +170,37 @@ class LangPermModel(models.Model):
     class Meta:
         ordering = ('-addTime',)
         verbose_name = '用户关联语种配置'
-        db_table = 'lang_perm'
+        db_table = 'lang_perm'
+
+
+class LangClassModel(models.Model):
+    id = models.AutoField(primary_key=True)
+    name = models.CharField(max_length=64, unique=True, verbose_name='avss中的context的name')
+
+    class Meta:
+        verbose_name = 'avss的模块表'
+        verbose_name_plural = verbose_name
+        db_table = 'lang_class'
+
+
+class LangKeyClassModel(models.Model):
+    id = models.AutoField(primary_key=True)
+    lk = models.ForeignKey(LangKeyModel, to_field='id', on_delete=models.CASCADE, verbose_name='关联词汇键表')
+    clazz = models.ForeignKey(LangClassModel, to_field='id', on_delete=models.CASCADE, verbose_name='关联avss模块表')
+
+    class Meta:
+        verbose_name = '词汇键与avss模块映射表'
+        verbose_name_plural = verbose_name
+        db_table = 'lang_key_class'
+
+
+class LangLocationModel(models.Model):
+    id = models.AutoField(primary_key=True)
+    lk = models.ForeignKey(LangKeyModel, to_field='id', on_delete=models.CASCADE, verbose_name='关联词汇键表')
+    filename = models.TextField(default='', null=False, verbose_name='类的路径')
+    line = models.IntegerField(default=0, verbose_name='所在的类的行')
+
+    class Meta:
+        verbose_name = 'avss的词汇的位置'
+        verbose_name_plural = verbose_name
+        db_table = 'lang_location'

+ 64 - 0
object/LanguageParser.py

@@ -0,0 +1,64 @@
+#!/usr/bin/env python3
+# -*- coding: utf-8 -*-
+
+
+import requests
+from xml.dom.minidom import parse
+import xml.dom.minidom
+
+
+class LanguageParser:
+
+    def parser(self, filename):
+        result = {}
+        domTree = xml.dom.minidom.parse(filename)
+        collection = domTree.documentElement
+
+        contexts = collection.getElementsByTagName('context')
+        for context in contexts:
+
+            name = context.getElementsByTagName('name')[0]
+            name = name.childNodes[0].data
+            print('name is %s' % name)
+
+            languages = {}
+            messages = context.getElementsByTagName('message')
+            for message in messages:
+                language = {}
+                source = message.getElementsByTagName('source')[0]
+                translation = message.getElementsByTagName('translation')[0]
+
+                language['source'] = source.childNodes[0].data
+                if translation.childNodes.length > 0:
+                    language['translation'] = translation.childNodes[0].data
+                else:
+                    language['translation'] = ''
+
+                # 取出location
+                locations = []
+                location_tags = message.getElementsByTagName('location')
+                for location_tag in location_tags:
+                    location = {}
+                    filename = location_tag.getAttribute('filename')
+                    line = location_tag.getAttribute('line')
+
+                    if filename:
+                        location['filename'] = filename
+                    else:
+                        location['filename'] = ''
+
+                    if line:
+                        location['line'] = line
+                    else:
+                        location['line'] = ''
+                    locations.append(location)
+
+                if len(locations) == 0:
+                    locations.append({'filename': '', 'line': 0})
+                language['locations'] = locations
+                languages[language['source']] = language
+            result[name] = {
+                'name': name,
+                'languages': languages
+            }
+        return result

+ 656 - 0
web/avss_index.html

@@ -0,0 +1,656 @@
+<!doctype html>
+<html lang="zh">
+<head>
+    <meta charset="UTF-8">
+    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
+    <meta name="viewport" content="width=device-width, initial-scale=1.0">
+    <title>afaa</title>
+    <link rel="stylesheet" type="text/css" href="css/normalize.css"/>
+    <link rel="stylesheet" type="text/css" href="css/default.css">
+    <link rel="stylesheet" href="css/style.css">
+    <link href="http://cdn.bootcss.com/font-awesome/4.4.0/css/font-awesome.min.css" rel="stylesheet">
+    <link href="css/bootstrap.min.css" rel="stylesheet">
+    <link href="http://cdnjs.cloudflare.com/ajax/libs/toastr.js/latest/css/toastr.min.css" rel="stylesheet">
+    <script src="https://npmcdn.com/tether@1.2.4/dist/js/tether.min.js"></script>
+    <script src="js/jquery.min.js"></script>
+    <script src="js/bootstrap.min.js"></script>
+    <script src="js/jquery_cookie_min.js"></script>
+    <script src="js/scripts.js"></script>
+    <script src="js/jqhttpsdk.js"></script>
+    <script src="js/jkcor.js"></script>
+    <script src="js/pages.js"></script>
+    <script src="js/datachange.js"></script>
+    <script src="http://cdnjs.cloudflare.com/ajax/libs/toastr.js/latest/toastr.min.js" type="text/javascript"></script>
+    <style>
+        td {
+            white-space: nowrap;
+        }
+        #in_button:hover{
+            background: black;
+            color: white;
+        }
+    </style>
+</head>
+<body>
+<div class="clear-backend">
+    <div class="avatar">
+        <div>
+            <a href="javascript:void(0);" target="_blank">
+                <img src="img/admin.png" alt="">
+            </a>
+        </div>
+    </div>
+
+    <!-- tab-menu -->
+    <input type="radio" class="tab-1" name="tab" onclick="location.href='index.html'">
+    <span>Home</span><i class="fa fa-home"></i>
+
+    <input type="radio" class="tab-5" name="tab" checked="checked">
+    <span>AVSS</span><i class="fa fa-language"></i>
+
+    <input type="radio" class="tab-2" name="tab" onclick="location.href='langTab.html'">
+    <span>Lang</span><i class="fa fa-medium"></i>
+
+    <input type="radio" class="tab-3" name="tab" onclick="location.href='userTab.html'">
+    <span>Users</span><i class="fa fa-user"></i>
+
+    <input type="radio" class="tab-4" name="tab" onclick="location.href='imgTab.html'">
+    <span>Azimg</span><i class="fa fa-image"></i>
+
+    <!--
+
+
+
+        <input type="radio" class="tab-5" name="tab">
+        <span>Upload</span><i class="fa fa-cloud-upload"></i>
+
+        <input type="radio" class="tab-6" name="tab">
+        <span>Favorite</span><i class="fa fa-star"></i>
+
+        <input type="radio" class="tab-7" name="tab">
+        <span>Photos</span><i class="fa fa-photo"></i>
+
+        <input type="radio" class="tab-8" name="tab">
+        <span>Analysis</span><i class="fa fa-line-chart"></i>
+
+        <input type="radio" class="tab-9" name="tab">
+        <span>Links</span><i class="fa fa-link"></i>
+
+        <input type="radio" class="tab-10" name="tab">
+        <span>Settings</span><i class="fa fa-cog"></i>-->
+
+    <!-- tab-top-bar -->
+    <center class="top-bar">
+        <input id="in_button" type="button" value="reset" style="border: 1px solid #e6cdcd; height: 60px; width: 100px;" onclick="onReset()">
+        <ul>
+            <li>
+                <a href="login.html" title="Log Out">
+                    <i class="fa fa-sign-out"></i>
+                </a>
+            </li>
+            <!--
+<li>
+    <a href="" title="Messages">
+        <i class="fa fa-envelope"></i>
+    </a>
+</li>
+<li>
+    <a href="" title="Edit">
+        <i class="fa fa-edit"></i>
+    </a>
+</li>
+            -->
+        </ul>
+    </center>
+
+    <!-- tab-content -->
+    <div class="tab-content" style="overflow: auto">
+        <section class="tab-item-1" style="height: 100%;width: 100%;display: block">
+            <div class="container-fluid">
+                <div class="row">
+                    <div id="searchCheckBox" class="col-md-8"></div>
+                    <div class="col-md-4">
+                        <input type="text" class="form-group form-control" id="searchInput"
+                               style="width: 300px;display: inline"/>
+                        <button class="btn btn-danger form-inline" style="margin-bottom: 5px"
+                                onclick="searchKeyAction()">搜索
+                        </button>
+                    </div>
+                </div>
+            </div>
+            <div class="container-fluid">
+                <div class="row">
+                    <!--add-->
+                    <div class="col-md-12">
+                        <table class="table table-bordered table-hover">
+                            <thead id="langTableHead"></thead>
+                            <tbody id="langTableBody"></tbody>
+                        </table>
+                    </div>
+                </div>
+                <div id="pagination"></div>
+
+            </div>
+
+
+            <!---->
+            <div class="container-fluid">
+                <div class="row">
+                    <div class="col-md-12">
+                        <div class="modal fade" id="modal-container-593541" role="dialog" aria-labelledby="myModalLabel"
+                             aria-hidden="true">
+                            <div class="modal-dialog" role="document">
+                                <div class="modal-content">
+                                    <div class="modal-header">
+                                        <h5 class="modal-title" id="myModalLabel">
+                                            EDIT
+                                        </h5>
+                                        <button type="button" class="close" data-dismiss="modal">
+                                            <span aria-hidden="true">×</span>
+                                        </button>
+                                    </div>
+                                    <div class="modal-body">
+                                        <div class="form-group" id="edit_model_form">
+                                            <!--<label for="InputLangArea">-->
+                                            <!--langArea-->
+                                            <!--</label>-->
+                                            <!--<input type="text" class="form-control" id="InputLangArea"/>-->
+                                        </div>
+                                    </div>
+                                    <div class="modal-footer">
+
+                                        <button type="button" class="btn btn-primary editRowSaveBtn"
+                                                onclick="editRow(this);return false;">
+                                            Save changes
+                                        </button>
+                                        <button type="button" class="btn btn-secondary" data-dismiss="modal">
+                                            Close
+                                        </button>
+                                    </div>
+                                </div>
+
+                            </div>
+
+                        </div>
+                    </div>
+                </div>
+            </div>
+
+            <!---->
+        </section>
+        <section class="tab-item-2">
+            <div class="container-fluid">
+                <div class="row">
+                    <div class="col-md-12">
+                    </div>
+                </div>
+            </div>
+        </section>
+    </div>
+</div>
+
+<script type="text/javascript">
+    var orderByupdate = 0
+    var page = 1
+    var line = 10
+    var initData
+    var IndexFlat = 0
+
+    $(function () {
+        toastr.options = {
+            "closeButton": true,
+            "debug": false,
+            "newestOnTop": false,
+            "progressBar": true,
+            "positionClass": "toast-top-right",
+            "preventDuplicates": false,
+            "onclick": null,
+            "showDuration": "300",
+            "hideDuration": "500",
+            "timeOut": "5000",
+            "extendedTimeOut": "1000",
+            "showEasing": "swing",
+            "hideEasing": "linear",
+            "showMethod": "fadeIn",
+            "hideMethod": "fadeOut"
+        }
+        var page = GetUrlParam('page')
+        if (!page) {
+            page = 1
+        }
+        let post_data = {
+            'token': $.cookie('access_token'),
+            'page': page,
+            'line': line,
+            'orderByupdate': orderByupdate,
+            'langType': 1
+        };
+        InitIndex(post_data)
+    });
+
+    function orderByUpdateTimeFunc(status) {
+        if (status === 1) {
+            orderByupdate = 0
+        } else {
+            orderByupdate = 1
+        }
+        var page = GetUrlParam('page')
+        if (!page) {
+            page = 1
+        }
+        let post_data = {
+            'token': $.cookie('access_token'),
+            'page': page,
+            'line': 10,
+            'orderByupdate': orderByupdate,
+            'langType': 1,
+        };
+        InitIndex(post_data)
+    }
+
+    function InitIndex(post_data) {
+        $.postJSON(
+            http_ip_prot + 'langWord/query', JSON.stringify(post_data),
+            function (data) {
+                if (data['code'] == 0) {
+                    // console.log(data['res'])
+                    console.log(data)
+                    addTable(data['res'])
+                    let count_page = Math.ceil(data['res']['count'] / line)
+                    $('#pagination').pagination({
+                        pages: count_page, //总页数
+                        // pages: 10000, //总页数
+                        edges: 2,
+                        cssStyle: 'pagination', //按纽大小pagination-lg或写入自定义css
+                        displayedPages: 5, //显示几个
+                        currentPage: GetUrlParam('page'),
+                        onPageClick: function (pageNumber, event) {
+                            //点击时调用
+                            // alert(pageNumber);
+                            queryData(pageNumber)
+                        },
+                        onInit: function (getid) {
+                            //刷新时或初始化调用
+                            // alert(getid);
+                        }
+                    });
+                } else {
+                    window.location.href = "http://" + domain + ":7724/web/login.html";
+                    alert(data['msg'])
+                }
+            }
+        );
+
+        $.postJSON(
+            http_ip_prot + 'user/init', JSON.stringify(post_data),
+            function (data) {
+                if (data['code'] == 0) {
+                    console.log('initData__start')
+                    console.log(data)
+                    console.log('initData__end')
+                    initData = data['res']
+                } else {
+                    window.location.href = "http://" + domain + ":7724/web/login.html";
+                    alert(data['msg'])
+                }
+            }
+        );
+    }
+
+    let la_list
+    let lw_data
+
+    function queryData(page) {
+        let searchKey = $('input[name="optionsRadios"]:checked').val();
+        let searchVal = $('#searchInput').val()
+        var post_data = {}
+        if (searchVal) {
+            post_data = {
+                'token': $.cookie('access_token'),
+                'page': page,
+                'line': 10,
+                'orderByupdate': orderByupdate,
+                'searchKey': searchKey,
+                'searchVal': searchVal,
+                'langType': 1
+            };
+        } else {
+            post_data = {
+                'token': $.cookie('access_token'),
+                'page': page,
+                'line': 10,
+                'orderByupdate': orderByupdate,
+                'langType': 1,
+            };
+        }
+
+        $.postJSON(
+            http_ip_prot + 'langWord/query', JSON.stringify(post_data),
+            function (data) {
+                if (data['code'] == 0) {
+                    // console.log(data['res'])
+                    console.log(data)
+                    addTable(data['res'])
+                } else {
+                    alert(data['msg'])
+                }
+            }
+        );
+    }
+
+    function addTable(data) {
+        //头部多区域语言
+        let head_data = data['la_list'];
+        la_list = head_data
+        // body部详细语言
+        let body_data = data['lw_dict'];
+        lw_data = body_data
+        let head_html = '<tr><th width="180px"><a href="javascript:void(0);" onclick=""></a></th><th>key</th>';
+        let search_tab = '<label><input type="radio" name="optionsRadios" value="key" checked>key</label>'
+
+        //头部标签添加
+
+        $.each(head_data.reverse(), function (idx, obj) {
+            head_html += ('<th>' + obj['lang'] + '</th>')
+            search_tab += '&nbsp;&nbsp;&nbsp;<label><input type="radio" name="optionsRadios" value="' + obj['lang'] + '">' + obj['lang'] + '</label>'
+        });
+        head_html += ('<th><a href="javascript:void(0);" onclick="orderByUpdateTimeFunc(' + orderByupdate + ')">udpateTime &nbsp;<i class="fa ' + (orderByupdate == 1 ? 'fa-arrow-up' : 'fa-arrow-down') + '" aria-hidden="true"></i></a></td></tr>');
+        // search_tab += '<td width="180px"><button class="btn-primary btn">搜索</button></td></tr>';
+        if (IndexFlat == 0) {
+            $('#searchCheckBox').html(search_tab)
+            IndexFlat = 1
+        }
+        let body_html = '';
+
+        console.log('--------');
+        $.each(body_data, function (idx, obj) {
+            let edit_btn = '<a href="javascript:void(0);" title="Edit" onclick="editFunc(this)"><i class="fa fa-edit"></i></a>';
+            let del_btn = '<a href="javascript:void(0);" title="Delete" onclick="deleteFunc(this)"><i class="fa fa-ban"></i></a>';
+            // let del_btn = '';
+            if(obj['status'] == 1){
+                body_html += '<tr style="background: red; color: white"><td>' + edit_btn + '&nbsp;&nbsp;&nbsp;' + del_btn + '</td>';
+            }else if(obj['status'] == 2){
+                body_html += '<tr style="background: blue; color: white"><td>' + edit_btn + '&nbsp;&nbsp;&nbsp;' + del_btn + '</td>';
+            }else{
+                body_html += '<tr><td>' + edit_btn + '&nbsp;&nbsp;&nbsp;' + del_btn + '</td>';
+            }
+
+            body_html += ('<td id="key">' + idx + '</td>');
+
+            $.each(la_list, function (x, y) {
+                if (obj[y['lang']]) {
+                    body_html += ('<td>' + obj[y['lang']] + '</td>')
+                } else {
+                    body_html += ('<td></td>')
+                }
+            });
+            let updTime = $.DateChange.UnixToDate(obj['updTime'], true, 8);
+            body_html += ('<td>' + updTime + '<span class="arrow dsc"></td></tr>');
+        });
+        $('#langTableHead').empty().html(head_html);
+        $('#langTableBody').empty().html(body_html);
+        addDelFunc()
+    }
+
+    function addRow() {
+        let save_btn = '<a href="javascript:void(0);" title="Save" class="save_row"><i class="fa fa-check-circle-o"></i></a>';
+        let del_btn = '<a href="javascript:void(0);" title="Delete" class="del_row"><i class="fa fa-ban"></i></a>';
+
+        let newRow = '<tr><td>' + save_btn + '&nbsp;&nbsp;&nbsp;' + del_btn + '</td><td><input class="form-control" type="text" langID="key" id="newRow_key"></td>'
+        $.each(la_list, function (idx, obj) {
+            // console.log(idx)
+            // newRow += ('<td>' + obj['id'] + '</td>')
+            newRow += ('<td>' +
+                '<input class="form-control" type="text" langID="' + obj['id'] + '" id="newRow_lang_' + obj['id'] + '">' +
+                '</td>')
+        })
+
+        newRow += '<td></td></tr>'
+        $('#langTableBody').prepend(newRow)
+        addDelFunc()
+        addSaveFunc()
+    }
+
+    function addDelFunc() {
+        $(".del_row").bind("click", function () {
+            let trRow = $(this).parent().parent()
+            trRow.remove()
+        });
+    }
+
+    function addSaveFunc() {
+
+        $(".save_row").bind("click", function () {
+            let post_data = {
+                'token': $.cookie('access_token')
+            }
+            let post_list = []
+            let trRow = $(this).parent().parent()
+            trRow.find('input').each(function () {
+                // console.log($(this).attr('id'))
+                // console.log($(this).attr('langID'))
+                let inputVal = $(this).val()
+                let langID = $(this).attr('langID')
+                if (langID === 'key') {
+                    post_data['word_key'] = inputVal
+                } else {
+                    post_list.push({'la_id': langID, 'val': inputVal})
+                }
+            })
+            post_data['word_arr'] = post_list
+            console.log(post_data)
+            $.postJSON(
+                http_ip_prot + 'langWord/add', JSON.stringify(post_data),
+                function (data) {
+                    if (data['code'] == 0) {
+                        // console.log(data['res'])
+                        window.location.reload();
+                        console.log(data)
+                    } else {
+                        alert(data['msg'])
+                    }
+                }
+            )
+        })
+    }
+
+
+    // 编辑模态框
+    function editFunc($this) {
+
+        let langKey = $($this).parent().parent().children().eq(1).text()
+        $('#modal-container-593541').modal('show')
+        let user_perm = initData['user_perm']
+        console.log(initData)
+        // let post_data = {'token': $.cookie('access_token')};
+        let html_per = '<label for="lang_key_edit">KEY</label><input class="form-control" ' + (user_perm == 1 ? '' : 'disabled="disabled"') + ' type="text" id="lang_key_edit" oldkey="' + langKey + '" value="' + langKey + '"> '
+        $.each(la_list, function (idx, obj) {
+            let lang_perm_ls = initData['lang_perm_ls']
+            let check_perm_flag = $.inArray(obj['lang'], lang_perm_ls)
+            if (check_perm_flag >= 0) {
+                var inputAttr = ''
+            } else {
+                var inputAttr = 'disabled="disabled"'
+            }
+            //console.log(obj);
+            html_per += ('<label for="InputLangArea">' + obj['lang'] + ':</label>' +
+                '<textarea type="text" ' + inputAttr + ' class="form-control disabled" lang="' + obj['lang'] + '">' + (lw_data[langKey][obj['lang']] ? lw_data[langKey][obj['lang']] : '') + '</textarea>')
+            //html_per += ('<label for="InputLangArea">' + obj['lang'] + ':</label>' +
+            //    '<input type="text" ' + inputAttr + ' class="form-control disabled" lang="' + obj['lang'] + '" value="' + (lw_data[langKey][obj['lang']] ? lw_data[langKey][obj['lang']] : '') + '"/>')
+        });
+        // console.log(html_per)
+        $('#edit_model_form').html(html_per)
+    }
+
+    function deleteFunc($this) {
+        let langKey = $($this).parent().parent().children().eq(1).text()
+
+        var r = confirm("Press a button")
+        if (r) {
+            let post_data = {
+                'token': $.cookie('access_token'),
+                'word_key': langKey
+            }
+            console.log(post_data)
+            $.postJSON(
+                http_ip_prot + 'avss/delete', JSON.stringify(post_data),
+                function (data) {
+                    if (data['code'] == 0) {
+                        // console.log(data['res'])
+                        console.log(data);
+                        alert(data['msg']);
+                        window.location.reload();
+                    } else {
+                        alert(data['msg'])
+                    }
+                }
+            )
+        }
+    }
+
+    /*post_data = {
+        word_key_id:1,
+        word_key:xxx,
+        word_arr:[
+            {'lang':'','val':''},
+            {'lang':'','val':''},
+            {'lang':'','val':''}
+        ]
+    }*/
+    function editRow() {
+        let post_data = {}
+
+        post_data['token'] = $.cookie('access_token')
+        post_data['word_key'] = $('#lang_key_edit').val()
+        post_data['old_word_key'] = $('#lang_key_edit').attr('oldkey')
+        post_data['word_arr'] = {}
+        post_data['status'] = 2
+        // $('#edit_model_form').find('input').each(function () {
+        //   let langArea = $(this).attr('lang')
+        // if (langArea) {
+        //   post_data['word_arr'][langArea] = $(this).val()
+        //}
+        //})
+        $('#edit_model_form').find('textarea').each(function () {
+            let langArea = $(this).attr('lang')
+            if (langArea) {
+                post_data['word_arr'][langArea] = $(this).val()
+            }
+        })
+        console.log(post_data)
+        $.postJSON(
+            http_ip_prot + 'langWord/update', JSON.stringify(post_data),
+            function (data) {
+                if (data['code'] == 0) {
+                    // console.log(data['res'])
+                    console.log(data)
+                    toastr["success"](data['msg'])
+                    $('#modal-container-593541').modal('hide')
+                    IndexTable()
+                    //window.location.reload();
+                } else {
+                    alert(data['msg'])
+                }
+            }
+        )
+        // $('.editRowSaveBtn').bind('click', function () {
+        //     console.log('adjslkfjsdalkfj')
+        // })
+    }
+
+    function IndexTable() {
+        var page = GetUrlParam('page')
+
+        if (!page) {
+            page = 1
+        }
+        let post_data = {
+            'token': $.cookie('access_token'),
+            'page': page,
+            'line': line,
+            'orderByupdate': orderByupdate,
+            'langType': 1,
+        };
+
+        $.postJSON(
+            http_ip_prot + 'langWord/query', JSON.stringify(post_data),
+            function (data) {
+                if (data['code'] == 0) {
+                    // console.log(data['res'])
+                    console.log(data)
+                    addTable(data['res'])
+                    let count_page = Math.ceil(data['res']['count'] / line)
+                    queryData(page)
+                } else {
+                    alert(data['msg'])
+                }
+            }
+        );
+    }
+
+    function searchKeyAction() {
+        var page = GetUrlParam('page')
+        if (!page) {
+            page = 1
+        }
+        let searchKey = $('input[name="optionsRadios"]:checked').val();
+        let searchVal = $('#searchInput').val()
+        console.log('-------------------------------')
+        console.log(searchKey)
+        console.log(searchVal)
+        console.log('-------------------------------')
+        let post_data = {}
+        if (searchVal && searchKey) {
+            post_data = {
+                'token': $.cookie('access_token'),
+                'page': page,
+                'line': 10,
+                'searchKey': searchKey,
+                'searchVal': searchVal
+            };
+        } else {
+            post_data = {
+                'token': $.cookie('access_token'),
+                'page': page,
+                'line': 10,
+            };
+        }
+        InitIndex(post_data)
+    }
+
+    function onReset() {
+        let role = $.cookie('role');
+        if(role == 1){
+            if(!confirm("如果你重置了语言状态,别的翻译者将无法查看到语言的相应状态!")){
+                return;
+            }
+        }
+        let post_data = {}
+        var word_key = '';
+        let table = $('#langTableBody').find('tr').each(function () {
+            var value = $(this).find('td:eq(1)').text();
+            word_key += value;
+            word_key += ',';
+        })
+        word_key = word_key.substr(0, word_key.length - 1);
+        post_data['word_key'] = word_key;
+        post_data['token'] = $.cookie('access_token');
+        $.postJSON(
+            http_ip_prot + 'langWord/reset', JSON.stringify(post_data),
+            function (data) {
+                if (data['code'] == 0) {
+                    // console.log(data['res'])
+                    console.log(data)
+                    toastr["success"](data['msg'])
+                    IndexTable()
+                    //window.location.reload();
+                } else {
+                    toastr["error"](data['msg'])
+                }
+            }
+        )
+
+    }
+</script>
+</body>
+</html>

+ 12 - 7
web/index.html

@@ -45,6 +45,9 @@
     <input type="radio" class="tab-1" name="tab" checked="checked">
     <span>Home</span><i class="fa fa-home"></i>
 
+    <input type="radio" class="tab-5" name="tab" onclick="location.href='avss_index.html'">
+    <span>AVSS</span><i class="fa fa-language"></i>
+
     <input type="radio" class="tab-2" name="tab" onclick="location.href='langTab.html'">
     <span>Lang</span><i class="fa fa-medium"></i>
 
@@ -219,7 +222,8 @@
             'token': $.cookie('access_token'),
             'page': page,
             'line': line,
-            'orderByupdate': orderByupdate
+            'orderByupdate': orderByupdate,
+            'langType': 0
         };
         InitIndex(post_data)
     });
@@ -239,13 +243,12 @@
             'page': page,
             'line': 10,
             'orderByupdate': orderByupdate,
-
+            'langType': 0
         };
         InitIndex(post_data)
     }
 
     function InitIndex(post_data) {
-
         $.postJSON(
             http_ip_prot + 'langWord/query', JSON.stringify(post_data),
             function (data) {
@@ -308,18 +311,19 @@
                 'line': 10,
                 'orderByupdate': orderByupdate,
                 'searchKey': searchKey,
-                'searchVal': searchVal
+                'searchVal': searchVal,
+                'langType': 0
             };
         } else {
             post_data = {
                 'token': $.cookie('access_token'),
                 'page': page,
                 'line': 10,
-                'orderByupdate': orderByupdate
+                'orderByupdate': orderByupdate,
+                'langType': 0
             };
         }
 
-
         $.postJSON(
             http_ip_prot + 'langWord/query', JSON.stringify(post_data),
             function (data) {
@@ -565,7 +569,8 @@
             'token': $.cookie('access_token'),
             'page': page,
             'line': line,
-            'orderByupdate': orderByupdate
+            'orderByupdate': orderByupdate,
+            'langType': 0
         };
         $.postJSON(
             http_ip_prot + 'langWord/query', JSON.stringify(post_data),

+ 8 - 2
web/langTab.html

@@ -31,6 +31,9 @@
     <input type="radio" class="tab-1" name="tab" onclick="location.href='index.html'">
     <span>Home</span><i class="fa fa-home"></i>
 
+    <input type="radio" class="tab-5" name="tab" onclick="location.href='avss_index.html'">
+    <span>AVSS</span><i class="fa fa-language"></i>
+
     <input type="radio" class="tab-2" name="tab" checked="checked">
     <span>Lang</span><i class="fa fa-medium"></i>
 
@@ -175,8 +178,9 @@
             let del_btn = '<a href="#" title="Delete" onclick="delArea(\'' + obj['id'] + '\')"><i class="fa fa-ban"></i></a>';
             let idw_btn = 'IOS:<a href="#" title="ios" onclick="dlFunc(\'' + obj['id'] + '\',1)"><i class="fa fa-download"></i></a>';
             let adw_btn = '安卓:<a href="#" title="android" onclick="dlFunc(\'' + obj['id'] + '\',2)"><i class="fa fa-download"></i></a>';
-            let np = '&nbsp;&nbsp;&nbsp;'
-            body_html += '<tr><td>' + obj['id'] + '</td><td>' + obj['lang'] + '</td><td>' + edit_btn + np + del_btn + np + idw_btn + np + adw_btn + '</td></tr>'
+            let avssw_btn = 'AVSS:<a href="#" title="avss" onclick="dlFunc(\'' + obj['id'] + '\',3)"><i class="fa fa-download"></i></a>';
+            let np = '&nbsp;&nbsp;&nbsp;&nbsp;'
+            body_html += '<tr><td>' + obj['id'] + '</td><td>' + obj['lang'] + '</td><td>' + edit_btn + np + del_btn + np + idw_btn + np + adw_btn + avssw_btn +'</td></tr>'
         })
         $('#tabLangBody').html(body_html)
     }
@@ -280,6 +284,8 @@
             post_type = 'ios'
         } else if (type == 2) {
             post_type = 'android'
+        }else if(type == 3){
+            post_type = 'avss'
         }
         let post_data = {
             'token': $.cookie('access_token'),

+ 3 - 0
web/userTab.html

@@ -31,6 +31,9 @@
     <input type="radio" class="tab-1" name="tab" onclick="location.href='index.html'">
     <span>Home</span><i class="fa fa-home"></i>
 
+    <input type="radio" class="tab-5" name="tab" onclick="location.href='avss_index.html'">
+    <span>AVSS</span><i class="fa fa-language"></i>
+
     <input type="radio" class="tab-2" name="tab" onclick="location.href='langTab.html'">
     <span>Lang</span><i class="fa fa-medium"></i>