diff --git a/object/application.go b/object/application.go index b14128eb..3777910d 100644 --- a/object/application.go +++ b/object/application.go @@ -24,16 +24,16 @@ type Application struct { Name string `xorm:"varchar(100) notnull pk" json:"name"` CreatedTime string `xorm:"varchar(100)" json:"createdTime"` - DisplayName string `xorm:"varchar(100)" json:"displayName"` - Logo string `xorm:"varchar(100)" json:"logo"` - HomepageUrl string `xorm:"varchar(100)" json:"homepageUrl"` - Description string `xorm:"varchar(100)" json:"description"` - Organization string `xorm:"varchar(100)" json:"organization"` - EnablePassword bool `json:"enablePassword"` - EnableSignUp bool `json:"enableSignUp"` - Providers []string `xorm:"varchar(1000)" json:"providers"` - ProviderObjs []*Provider `xorm:"-" json:"providerObjs"` - OrganizationObj *Organization `xorm:"-" json:"organizationObj"` + DisplayName string `xorm:"varchar(100)" json:"displayName"` + Logo string `xorm:"varchar(100)" json:"logo"` + HomepageUrl string `xorm:"varchar(100)" json:"homepageUrl"` + Description string `xorm:"varchar(100)" json:"description"` + Organization string `xorm:"varchar(100)" json:"organization"` + EnablePassword bool `json:"enablePassword"` + EnableSignUp bool `json:"enableSignUp"` + Providers []ProviderItem `xorm:"varchar(1000)" json:"providers"` + ProviderObjs []*Provider `xorm:"-" json:"providerObjs"` + OrganizationObj *Organization `xorm:"-" json:"organizationObj"` ClientId string `xorm:"varchar(100)" json:"clientId"` ClientSecret string `xorm:"varchar(100)" json:"clientSecret"` @@ -68,8 +68,8 @@ func extendApplicationWithProviders(application *Application) { } application.ProviderObjs = []*Provider{} - for _, providerName := range application.Providers { - if provider, ok := m[providerName]; ok { + for _, providerItem := range application.Providers { + if provider, ok := m[providerItem.Name]; ok { application.ProviderObjs = append(application.ProviderObjs, provider) } } @@ -183,8 +183,8 @@ func (application *Application) getProviderByCategory(category string) *Provider m[provider.Name] = provider } - for _, providerName := range application.Providers { - if provider, ok := m[providerName]; ok { + for _, providerItem := range application.Providers { + if provider, ok := m[providerItem.Name]; ok { return provider } } diff --git a/object/init.go b/object/init.go index e736e585..efca1723 100644 --- a/object/init.go +++ b/object/init.go @@ -66,7 +66,7 @@ func initBuiltInApplication() { Organization: "built-in", EnablePassword: true, EnableSignUp: true, - Providers: []string{}, + Providers: []ProviderItem{}, RedirectUris: []string{}, ExpireInHours: 168, } diff --git a/object/provider.go b/object/provider.go index bf4f8d9b..27296289 100644 --- a/object/provider.go +++ b/object/provider.go @@ -19,6 +19,13 @@ import ( "xorm.io/core" ) +type ProviderItem struct { + Name string `json:"name"` + CanSignUp bool `json:"canSignUp"` + CanSignIn bool `json:"canSignIn"` + CanUnbind bool `json:"canUnbind"` +} + type Provider struct { Owner string `xorm:"varchar(100) notnull pk" json:"owner"` Name string `xorm:"varchar(100) notnull pk" json:"name"` diff --git a/web/src/ApplicationEditPage.js b/web/src/ApplicationEditPage.js index 4240c3ba..202551a3 100644 --- a/web/src/ApplicationEditPage.js +++ b/web/src/ApplicationEditPage.js @@ -23,6 +23,7 @@ import SignupPage from "./auth/SignupPage"; import LoginPage from "./auth/LoginPage"; import i18next from "i18next"; import UrlTable from "./UrlTable"; +import ProviderTable from "./ProviderTable"; const { Option } = Select; @@ -272,15 +273,12 @@ class ApplicationEditPage extends React.Component { {i18next.t("general:Providers")}: - + { this.updateApplicationField('providers', value)}} + /> diff --git a/web/src/ProviderTable.js b/web/src/ProviderTable.js new file mode 100644 index 00000000..11d0aba6 --- /dev/null +++ b/web/src/ProviderTable.js @@ -0,0 +1,177 @@ +// Copyright 2021 The casbin Authors. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +import React from "react"; +import {DownOutlined, DeleteOutlined, UpOutlined, LinkOutlined} from '@ant-design/icons'; +import {Button, Col, Input, Row, Select, Switch, Table, Tooltip} from 'antd'; +import * as Setting from "./Setting"; +import i18next from "i18next"; + +const { Option } = Select; + +class ProviderTable extends React.Component { + constructor(props) { + super(props); + this.state = { + classes: props, + }; + } + + updateTable(table) { + this.props.onUpdateTable(table); + } + + updateField(table, index, key, value) { + table[index][key] = value; + this.updateTable(table); + } + + addRow(table) { + let row = {name: "", canSignUp: false, canSignIn: true, canUnbind: true}; + if (table === undefined) { + table = []; + } + table = Setting.addRow(table, row); + this.updateTable(table); + } + + deleteRow(table, i) { + table = Setting.deleteRow(table, i); + this.updateTable(table); + } + + upRow(table, i) { + table = Setting.swapRow(table, i - 1, i); + this.updateTable(table); + } + + downRow(table, i) { + table = Setting.swapRow(table, i, i + 1); + this.updateTable(table); + } + + renderTable(table) { + const columns = [ + { + title: i18next.t("provider:Name"), + dataIndex: 'name', + key: 'name', + render: (text, record, index) => { + return ( + + ) + return ( + } value={text} onChange={e => { + this.updateField(table, index, 'name', e.target.value); + }} /> + ) + } + }, + { + title: i18next.t("provider:canSignUp"), + dataIndex: 'canSignUp', + key: 'canSignUp', + width: '120px', + render: (text, record, index) => { + return ( + { + this.updateField(table, index, 'canSignUp', checked); + }} /> + ) + } + }, + { + title: i18next.t("provider:canSignIn"), + dataIndex: 'canSignIn', + key: 'canSignIn', + width: '120px', + render: (text, record, index) => { + return ( + { + this.updateField(table, index, 'canSignIn', checked); + }} /> + ) + } + }, + { + title: i18next.t("provider:canUnbind"), + dataIndex: 'canUnbind', + key: 'canUnbind', + width: '120px', + render: (text, record, index) => { + return ( + { + this.updateField(table, index, 'canUnbind', checked); + }} /> + ) + } + }, + { + title: i18next.t("general:Action"), + key: 'action', + width: '100px', + render: (text, record, index) => { + return ( +
+ +
+ ); + } + }, + ]; + + return ( + ( +
+ {this.props.title}     + +
+ )} + /> + ); + } + + render() { + return ( +
+ +
+ { + this.renderTable(this.props.table) + } + + + + ) + } +} + +export default ProviderTable;