diff --git a/src/workbench/browser/src/app/pages/api/api-routing.module.ts b/src/workbench/browser/src/app/pages/api/api-routing.module.ts index cdf8c554..9ab29801 100644 --- a/src/workbench/browser/src/app/pages/api/api-routing.module.ts +++ b/src/workbench/browser/src/app/pages/api/api-routing.module.ts @@ -4,6 +4,7 @@ import { Routes, RouterModule } from '@angular/router'; import { ApiComponent } from './api.component'; import { ApiDetailComponent } from './detail/api-detail.component'; import { ApiEditComponent } from './edit/api-edit.component'; +import { ApiOverviewComponent } from './overview/api-overview.component'; import { ApiTestComponent } from './test/api-test.component'; const routes: Routes = [ @@ -16,6 +17,10 @@ const routes: Routes = [ redirectTo: 'test', pathMatch: 'full', }, + { + path: 'overview', + component: ApiOverviewComponent, + }, { path: 'detail', component: ApiDetailComponent, diff --git a/src/workbench/browser/src/app/pages/api/api.component.scss b/src/workbench/browser/src/app/pages/api/api.component.scss index 84dfad73..13982387 100644 --- a/src/workbench/browser/src/app/pages/api/api.component.scss +++ b/src/workbench/browser/src/app/pages/api/api.component.scss @@ -16,29 +16,12 @@ nz-sider { ::ng-deep { .ant-layout-sider-children { + border-right: 1px solid #f0f0f0; padding: 5px; .group-btn-add, .group-search { margin-bottom: 12px; } - .group-tree { - overflow: auto; - height: calc(100vh - 129px); - .ant-tree-switcher { - width: 12px; - } - .ant-tree-indent-unit { - width: 8px; - } - .ant-tree { - .ant-tree-node-content-wrapper { - padding: 0 2px; - } - } - } - } - .ant-layout-sider-children { - border-right: 1px solid #f0f0f0; } .tabs-bar { background-color: var(--SEC_BG); diff --git a/src/workbench/browser/src/app/pages/api/api.module.ts b/src/workbench/browser/src/app/pages/api/api.module.ts index cf0f84b7..0d732935 100644 --- a/src/workbench/browser/src/app/pages/api/api.module.ts +++ b/src/workbench/browser/src/app/pages/api/api.module.ts @@ -7,11 +7,11 @@ import { ApiDetailModule } from './detail/api-detail.module'; import { ApiTestModule } from './test/api-test.module'; import { EnvModule } from '../env/env.module'; import { EouiModule } from '../../eoui/eoui.module'; -import { ParamsImportModule } from '../../shared/components/params-import/params-import.module'; import { ApiComponent } from './api.component'; import { ApiGroupEditComponent } from './group/edit/api-group-edit.component'; import { ExportApiComponent } from '../../shared/components/export-api/export-api.component'; +import { SyncApiComponent } from '../../shared/components/sync-api/sync-api.component'; import { NzRadioModule } from 'ng-zorro-antd/radio'; import { NzButtonModule } from 'ng-zorro-antd/button'; import { NzIconModule } from 'ng-zorro-antd/icon'; @@ -21,6 +21,9 @@ import { NzTreeModule } from 'ng-zorro-antd/tree'; import { NzFormModule } from 'ng-zorro-antd/form'; import { NzInputModule } from 'ng-zorro-antd/input'; import { NzDropDownModule } from 'ng-zorro-antd/dropdown'; +import { NzDividerModule } from 'ng-zorro-antd/divider'; +import { NzCardModule } from 'ng-zorro-antd/card'; + import { ApiTabService } from './tab/api-tab.service'; import { MessageService } from '../../shared/services/message'; @@ -29,8 +32,9 @@ import { ApiTabComponent } from './tab/api-tab.component'; import { ApiService } from './api.service'; import { ElectronService } from '../../core/services'; import { StorageService } from '../../shared/services/storage'; +import { ApiOverviewComponent } from './overview/api-overview.component'; -const COMPONENTS = [ApiComponent, ApiGroupEditComponent, ApiGroupTreeComponent, ExportApiComponent]; +const COMPONENTS = [ApiComponent, ApiGroupEditComponent, ApiGroupTreeComponent, ExportApiComponent,SyncApiComponent]; @NgModule({ imports: [ FormsModule, @@ -49,11 +53,12 @@ const COMPONENTS = [ApiComponent, ApiGroupEditComponent, ApiGroupTreeComponent, NzInputModule, NzRadioModule, NzDropDownModule, - ParamsImportModule, + NzDividerModule, EouiModule, EnvModule, + NzCardModule ], - declarations: [...COMPONENTS, ApiTabComponent], + declarations: [...COMPONENTS, ApiTabComponent, ApiOverviewComponent], exports: [], providers: [ElectronService, MessageService, ApiTabService, ApiService, StorageService], }) diff --git a/src/workbench/browser/src/app/pages/api/api.service.ts b/src/workbench/browser/src/app/pages/api/api.service.ts index 81b9519e..a3531a24 100644 --- a/src/workbench/browser/src/app/pages/api/api.service.ts +++ b/src/workbench/browser/src/app/pages/api/api.service.ts @@ -31,7 +31,7 @@ export class ApiService { nzOnOk: () => { this.storage.run('apiDataRemove', [apiData.uuid], (result: StorageHandleResult) => { if (result.status === StorageHandleStatus.success) { - this.messageService.send({ type: 'deleteApi', data: { uuid: apiData.uuid } }); + this.messageService.send({ type: 'deleteApiSuccess', data: { uuid: apiData.uuid } }); } }); }, @@ -40,20 +40,12 @@ export class ApiService { bulkDelete(apis) { this.storage.run('apiDataBulkRemove', [apis], (result: StorageHandleResult) => { if (result.status === StorageHandleStatus.success) { - this.messageService.send({ type: 'bulkDeleteApi', data: { uuids: apis } }); + this.messageService.send({ type: 'bulkDeleteApiSuccess', data: { uuids: apis } }); } }); } export(apiData: ApiData) { - const modal: NzModalRef = this.modalService.create({ - nzTitle: "导出 API", - nzContent: ExportApiComponent, - nzClosable: false, - nzComponentParams:{}, - nzOnOk() { - modal.componentInstance.submit(); - }, - }); + } bulkExport(groups) {} } diff --git a/src/workbench/browser/src/app/pages/api/edit/api-edit.component.ts b/src/workbench/browser/src/app/pages/api/edit/api-edit.component.ts index 1301d061..6289ec61 100644 --- a/src/workbench/browser/src/app/pages/api/edit/api-edit.component.ts +++ b/src/workbench/browser/src/app/pages/api/edit/api-edit.component.ts @@ -82,7 +82,6 @@ export class ApiEditComponent implements OnInit, OnDestroy { treeItems.sort((a, b) => a.weight - b.weight); } listToTree(treeItems, this.groups, '0'); - console.log(treeItems, this.groups); this.afterInitGroup(); }); } diff --git a/src/workbench/browser/src/app/pages/api/edit/api-edit.module.ts b/src/workbench/browser/src/app/pages/api/edit/api-edit.module.ts index 4e875366..0aa7046b 100644 --- a/src/workbench/browser/src/app/pages/api/edit/api-edit.module.ts +++ b/src/workbench/browser/src/app/pages/api/edit/api-edit.module.ts @@ -43,7 +43,7 @@ const NZ_COMPONETS = [ NzTabsModule, NzRadioModule, NzDividerModule, - NzAffixModule + NzAffixModule, ]; const COMPONENTS = [ ApiEditComponent, diff --git a/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.html b/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.html index 43f8369b..3c250c04 100644 --- a/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.html +++ b/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.html @@ -22,7 +22,6 @@ @@ -30,7 +29,27 @@ -
+ +
+ + +
+
+ + {{ node.title }} +
+
+
+
+
+ +
-
+
{{ node.origin.method.slice(0, 4) @@ -104,13 +123,22 @@
  • 编辑
  • -
  • +
  • 复制
  • -
  • +
  • 导出 API
  • -
  • +
  • 删除
  • diff --git a/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.scss b/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.scss index 7bb01053..d6ab6998 100644 --- a/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.scss +++ b/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.scss @@ -2,14 +2,39 @@ .ant-tree-node-selected * { color: var(--TEXT_ACTIVE); } + .ant-tree-list-holder-inner { + .nz-tree-node:first { + border-bottom: 1px solid var(--BORDER); + } + } + .fixed_group_tree { + nz-tree-node-switcher { + display: none; + } + } +} +.group_tree { + overflow: auto; + height: calc(100vh - 129px); + .ant-tree-switcher { + width: 12px; + } + .ant-tree-indent-unit { + width: 8px; + } + .ant-tree { + .ant-tree-node-content-wrapper { + padding: 0 2px; + } + } } .ant-dropdown-menu { min-width: 100px; } -.method_text{ +.method_text { width: 32px; } -.node_title{ +.node_title { max-width: 145px; } .tree_node { diff --git a/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.ts b/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.ts index d0379282..c01123f5 100644 --- a/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.ts +++ b/src/workbench/browser/src/app/pages/api/group/tree/api-group-tree.component.ts @@ -51,7 +51,17 @@ export class ApiGroupTreeComponent implements OnInit, OnDestroy { * Level Tree nodes. */ treeNodes: GroupTreeItem[] | NzTreeNode[] | any; - nzSelectedKeys: number[]; + fixedTreeNode: GroupTreeItem[] | NzTreeNode[] = [ + { + title: '概况', + key: 'overview', + weight: 0, + parentID: '0', + isLeaf: true, + isFixed: true, + }, + ]; + nzSelectedKeys: number[]=[]; private destroy$: Subject = new Subject(); constructor( private router: Router, @@ -91,7 +101,6 @@ export class ApiGroupTreeComponent implements OnInit, OnDestroy { } getGroups() { this.storage.run('groupLoadAllByProjectID', [this.projectID], (result: StorageHandleResult) => { - console.log('groupLoadAllByProjectID'); if (result.status === StorageHandleStatus.success) { result.data.forEach((item) => { delete item.updatedAt; @@ -103,6 +112,7 @@ export class ApiGroupTreeComponent implements OnInit, OnDestroy { parentID: item.parentID ? `group-${item.parentID}` : '0', isLeaf: false, }); + console.log(this.treeItems); }); } this.getApis(); @@ -184,12 +194,23 @@ export class ApiGroupTreeComponent implements OnInit, OnDestroy { * @param event */ clickTreeItem(event: NzFormatEmitEvent): void { - if (!event.node.isLeaf) { - event.node.isExpanded = !event.node.isExpanded; - this.toggleExpand(); - } else { - event.eventName = 'detailApi'; - this.operateApiEvent(event); + let eventName=!event.node.isLeaf?'clickFolder':event.node?.origin.isFixed?'clickFixedItem':'clickItem'; + switch(eventName){ + case 'clickFolder':{ + event.node.isExpanded = !event.node.isExpanded; + this.toggleExpand(); + break; + } + case 'clickFixedItem':{ + event.eventName = 'detailOverview'; + this.operateApiEvent(event); + break; + } + case 'clickItem':{ + event.eventName = 'detailApi'; + this.operateApiEvent(event); + break; + } } } diff --git a/src/workbench/browser/src/app/pages/api/overview/api-overview.component.html b/src/workbench/browser/src/app/pages/api/overview/api-overview.component.html new file mode 100644 index 00000000..7d85f48f --- /dev/null +++ b/src/workbench/browser/src/app/pages/api/overview/api-overview.component.html @@ -0,0 +1,27 @@ +
    +

    概况

    + +
    +
    +
    + + + + + + +
    +
    + + + + + + +
    +
    + +
    +
    diff --git a/src/workbench/browser/src/app/pages/api/overview/api-overview.component.scss b/src/workbench/browser/src/app/pages/api/overview/api-overview.component.scss new file mode 100644 index 00000000..0ee23055 --- /dev/null +++ b/src/workbench/browser/src/app/pages/api/overview/api-overview.component.scss @@ -0,0 +1,8 @@ +.overview_container{ + width: 50%; + margin: 0 auto; + padding: 20px 0; +} +nz-card{ + min-width: 220px; +} \ No newline at end of file diff --git a/src/workbench/browser/src/app/pages/api/overview/api-overview.component.spec.ts b/src/workbench/browser/src/app/pages/api/overview/api-overview.component.spec.ts new file mode 100644 index 00000000..b7bd76ed --- /dev/null +++ b/src/workbench/browser/src/app/pages/api/overview/api-overview.component.spec.ts @@ -0,0 +1,25 @@ +import { ComponentFixture, TestBed } from '@angular/core/testing'; + +import { ApiOverviewComponent } from './api-overview.component'; + +describe('ApiOverviewComponent', () => { + let component: ApiOverviewComponent; + let fixture: ComponentFixture; + + beforeEach(async () => { + await TestBed.configureTestingModule({ + declarations: [ ApiOverviewComponent ] + }) + .compileComponents(); + }); + + beforeEach(() => { + fixture = TestBed.createComponent(ApiOverviewComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); +}); diff --git a/src/workbench/browser/src/app/pages/api/overview/api-overview.component.ts b/src/workbench/browser/src/app/pages/api/overview/api-overview.component.ts new file mode 100644 index 00000000..9b71d4d7 --- /dev/null +++ b/src/workbench/browser/src/app/pages/api/overview/api-overview.component.ts @@ -0,0 +1,38 @@ +import { Component, OnInit } from '@angular/core'; +import { NzModalRef } from 'ng-zorro-antd/modal'; +import { ExportApiComponent } from '../../../shared/components/export-api/export-api.component'; +import { SyncApiComponent } from '../../../shared/components/sync-api/sync-api.component'; +import { ModalService } from '../../../shared/services/modal.service'; + +@Component({ + selector: 'eo-api-overview', + templateUrl: './api-overview.component.html', + styleUrls: ['./api-overview.component.scss'], +}) +export class ApiOverviewComponent implements OnInit { + constructor(private modalService: ModalService) {} + + ngOnInit(): void {} + export() { + const modal: NzModalRef = this.modalService.create({ + nzTitle: '导出 API', + nzContent: ExportApiComponent, + nzClosable: false, + nzComponentParams: {}, + nzOnOk() { + modal.componentInstance.submit(); + }, + }); + } + sync() { + const modal: NzModalRef = this.modalService.create({ + nzTitle: '推送 API', + nzContent: SyncApiComponent, + nzClosable: false, + nzComponentParams: {}, + nzOnOk() { + modal.componentInstance.submit(); + }, + }); + } +} diff --git a/src/workbench/browser/src/app/pages/api/tab/api-tab.component.ts b/src/workbench/browser/src/app/pages/api/tab/api-tab.component.ts index a3318865..8af15674 100644 --- a/src/workbench/browser/src/app/pages/api/tab/api-tab.component.ts +++ b/src/workbench/browser/src/app/pages/api/tab/api-tab.component.ts @@ -24,6 +24,7 @@ export class ApiTabComponent implements OnInit, OnDestroy { edit: { path: '/home/api/edit', title: '新 API' }, test: { path: '/home/api/test', title: '新 API' }, detail: { path: '/home/api/detail', title: 'API 详情' }, + overview: { path: '/home/api/overview', title: '概况', key: 'overview' }, }; MAX_TAB_LIMIT = 15; @@ -52,22 +53,22 @@ export class ApiTabComponent implements OnInit, OnDestroy { */ private initTab() { let apiID = Number(this.route.snapshot.queryParams.uuid); - let hasApiExist = this.apiDataItems[apiID]; - //delete api - if (!hasApiExist) { - this.closeTab({ index: this.selectedIndex }); - return; - } - if (apiID) { - const tab = this.getTabInfo({ - tabData: this.apiDataItems[apiID], - }); - this.appendOrSwitchTab('unset', tab); - } else { + if (!apiID) { let module = Object.keys(this.defaultTabs).find((keyName) => this.router.url.split('?')[0].includes(this.defaultTabs[keyName].path) ); this.appendOrSwitchTab(module, this.route.snapshot.queryParams); + } else { + let isApiExist = this.apiDataItems[apiID]; + //not exist api or delete api + if (!isApiExist) { + this.closeTab({ index: this.selectedIndex }); + return; + } + const tab = this.getTabInfo({ + tabData: this.apiDataItems[apiID], + }); + this.appendOrSwitchTab('unset', tab); } } /** @@ -83,18 +84,22 @@ export class ApiTabComponent implements OnInit, OnDestroy { which === 'unset' ? {} : this.defaultTabs[which], tabContent ); - let existApiIndex = this.tabSerive.tabs.findIndex((val) => val.key === tab.key); - if (tab.key && existApiIndex !== -1) { + let existTabIndex = this.tabSerive.tabs.findIndex((val) => val.key === tab.key); + if (tab.key && existTabIndex !== -1) { let switchTab = {}; - if (this.tabSerive.tabs[existApiIndex].path !== tab.path) { + if (this.tabSerive.tabs[existTabIndex].path !== tab.path) { //* exist api in same tab change route,such as edit page to detail switchTab['path'] = tab.path; } - this.switchTab(existApiIndex, switchTab); + this.switchTab(existTabIndex, switchTab); return; } // avoid open too much tab,if detail or no change,open page in current tab - if(this.tabSerive.tabs.length&&this.tabSerive.currentTab?.path.includes('detail')&&tab.path.includes('detail')){ + if ( + this.tabSerive.tabs.length && + this.tabSerive.currentTab?.path.includes('detail') && + tab.path.includes('detail') + ) { this.switchTab(this.selectedIndex, tab); return; } @@ -222,12 +227,17 @@ export class ApiTabComponent implements OnInit, OnDestroy { case 'detailApi': this.appendOrSwitchTab('detail', inArg.data.origin); break; + case 'detailOverview': { + console.log(inArg.data.origin); + this.appendOrSwitchTab('overview', inArg.data.origin); + break; + } case 'gotoEditApi': this.appendOrSwitchTab('edit', inArg.data.origin); break; case 'copyApi': case 'gotoAddApi': - this.appendOrSwitchTab('edit', inArg.data ? { groupID: inArg.data.key.replace('group-','') } : {}); + this.appendOrSwitchTab('edit', inArg.data ? { groupID: inArg.data.key.replace('group-', '') } : {}); break; case 'addApiSuccess': case 'editApiSuccess': diff --git a/src/workbench/browser/src/app/shared/components/export-api/export-api.component.html b/src/workbench/browser/src/app/shared/components/export-api/export-api.component.html index 12463c04..6546b723 100644 --- a/src/workbench/browser/src/app/shared/components/export-api/export-api.component.html +++ b/src/workbench/browser/src/app/shared/components/export-api/export-api.component.html @@ -1,4 +1,3 @@ - - + \ No newline at end of file diff --git a/src/workbench/browser/src/app/shared/components/export-api/export-api.component.ts b/src/workbench/browser/src/app/shared/components/export-api/export-api.component.ts index d90f7fd5..a2167522 100644 --- a/src/workbench/browser/src/app/shared/components/export-api/export-api.component.ts +++ b/src/workbench/browser/src/app/shared/components/export-api/export-api.component.ts @@ -1,6 +1,5 @@ import { Component, Input, OnInit } from '@angular/core'; import { NzModalRef } from 'ng-zorro-antd/modal'; -import { MessageService } from '../../../shared/services/message'; import { StorageService } from '../../../shared/services/storage'; @Component({ @@ -9,15 +8,29 @@ import { StorageService } from '../../../shared/services/storage'; styleUrls: ['./export-api.component.scss'], }) export class ExportApiComponent implements OnInit { - exportType:'eoapi' - constructor( - private modalRef: NzModalRef, - private storage: StorageService - ) { } - - ngOnInit(): void { - } - submit(){ - console.log('export') + exportType: string = 'eoapi'; + supportList: any[] = [ + { + key: 'eoapi', + image:'', + title: 'Eoapi(.json)', + }, + { + key: 'openapi3', + image:'', + title: 'Swagger V3.0', + }, + ]; + constructor(private modalRef: NzModalRef, private storage: StorageService) {} + ngOnInit(): void {} + exportEoapi() {} + submit() { + switch (this.exportType) { + case 'eoapi': { + this.exportEoapi(); + break; + } + } + console.log('export'); } } diff --git a/src/workbench/browser/src/app/shared/components/navbar/navbar.component.html b/src/workbench/browser/src/app/shared/components/navbar/navbar.component.html index b17bfb4a..8bc64324 100644 --- a/src/workbench/browser/src/app/shared/components/navbar/navbar.component.html +++ b/src/workbench/browser/src/app/shared/components/navbar/navbar.component.html @@ -15,7 +15,7 @@
    - + diff --git a/src/workbench/browser/src/app/shared/components/navbar/navbar.component.ts b/src/workbench/browser/src/app/shared/components/navbar/navbar.component.ts index 6e639ead..c0167621 100644 --- a/src/workbench/browser/src/app/shared/components/navbar/navbar.component.ts +++ b/src/workbench/browser/src/app/shared/components/navbar/navbar.component.ts @@ -31,6 +31,7 @@ export class NavbarComponent implements OnInit { constructor(private electron: ElectronService) { this.isElectron = this.electron.isElectron; + this.getInstaller(); } getInstaller() { fetch('https://api.github.com/repos/eolinker/eoapi/releases') diff --git a/src/workbench/browser/src/app/shared/components/sync-api/sync-api.component.html b/src/workbench/browser/src/app/shared/components/sync-api/sync-api.component.html new file mode 100644 index 00000000..35bb0f86 --- /dev/null +++ b/src/workbench/browser/src/app/shared/components/sync-api/sync-api.component.html @@ -0,0 +1,5 @@ + + + + + diff --git a/src/workbench/browser/src/app/shared/components/sync-api/sync-api.component.scss b/src/workbench/browser/src/app/shared/components/sync-api/sync-api.component.scss new file mode 100644 index 00000000..e69de29b diff --git a/src/workbench/browser/src/app/shared/components/sync-api/sync-api.component.ts b/src/workbench/browser/src/app/shared/components/sync-api/sync-api.component.ts new file mode 100644 index 00000000..a150361a --- /dev/null +++ b/src/workbench/browser/src/app/shared/components/sync-api/sync-api.component.ts @@ -0,0 +1,22 @@ +import { Component, Input, OnInit } from '@angular/core'; +import { NzModalRef } from 'ng-zorro-antd/modal'; +import { StorageService } from '../../services/storage'; + +@Component({ + selector: 'eo-sync-api', + templateUrl: './sync-api.component.html', + styleUrls: ['./sync-api.component.scss'], +}) +export class SyncApiComponent implements OnInit { + exportType: string = 'eolink'; + constructor( + private modalRef: NzModalRef, + private storage: StorageService + ) { } + + ngOnInit(): void { + } + submit(){ + console.log('export') + } +} diff --git a/src/workbench/browser/src/app/shared/models/tree.model.ts b/src/workbench/browser/src/app/shared/models/tree.model.ts index 9223eabb..6c618491 100644 --- a/src/workbench/browser/src/app/shared/models/tree.model.ts +++ b/src/workbench/browser/src/app/shared/models/tree.model.ts @@ -38,6 +38,14 @@ export interface GroupTreeItem { */ isLeaf: boolean; + /** + * Item or folder + * If true, it means fixed group + * + * @type {boolean} + */ + isFixed?: boolean; + /** * Api data request method. only for display. *