劉玥 高銘 文超 丁鑫
關(guān)鍵詞:次級排課系統(tǒng);權(quán)限驗證;數(shù)據(jù)同步
1后端資源的權(quán)限管理
后端的接口實際上是一種資源,為了方便后端資源的開發(fā)與維護,本系統(tǒng)將后端資源劃分為以下兩種。
(1)用戶使用的資源(下稱用戶接口)。
(2)所有人都能使用的資源(下稱通用接口)。
不同資源的受眾、用途以及重要程度不盡相同,導致它們的開放性也有所差別。其中,還對用戶接口的訪問采取了權(quán)限控制,即不同角色的用戶可以訪問的接口是不一樣的。
1.1資源的開放性
用戶接口暴露的數(shù)據(jù)涉及每個用戶的私人信息,因此需要較為嚴格的鑒權(quán)機制來管控;相比之下,通用接口通常標識著一些不重要的資源,如系統(tǒng)中的一些常量,因此不需要任何權(quán)限控制,來者不拒。
1.2接口的認證機制
1.2.1令牌
用戶接口的訪問需要受到管制,所以必須有一套機制來實現(xiàn)這個目的。本系統(tǒng)采用token鑒權(quán)機制。
在本系統(tǒng)中,用戶接口的token稱為login-token,它們都是接口受眾的臨時憑證。無論是login-token還是app-access-token,其中只攜帶相關(guān)實體的id,login-token中攜帶的是系統(tǒng)用戶的id,app-access-token中則攜帶了第三方程序的id。
1.2.2令牌的頒發(fā)
login-token的頒發(fā)由接口/auth _user接口頒發(fā)。前端訪問該接口時,需要攜帶用戶名和密碼,/auth—user接口認證用戶名密碼無誤后,下發(fā)用戶令牌。前端妥善保存令牌,在訪問用戶接口時,將該令牌置于header login-token中,以表明用戶身份。
1.2.3令牌失效
上文提及的兩種令牌都有一定的時效,調(diào)用者在必要時可以通過令牌時效查詢接口、令牌是否有效,若令牌失效,則需要重新向相應(yīng)的令牌頒發(fā)接口申請新的令牌。login-token的時效查詢接口是/token—expire,app-access-token的時效查詢接口是/app—access_token/token-expire.
1.3用戶接口
與用戶交互的前端需要通過用戶接口來獲取數(shù)據(jù)并展示給用戶。用戶接口的訪問者必須在HTTP請求中攜帶用戶的token,以證明自己是系統(tǒng)中的合法用戶。
1.4用戶Token認證機制
1.4.1頒發(fā)login-token
前端調(diào)用接口/auth—user,并攜帶用戶的用戶名和密碼,如果經(jīng)查詢,數(shù)據(jù)庫中有相應(yīng)的用戶記錄,則生成token并通過響應(yīng)返回前端。前端保存該token,可以用來訪問其他用戶接口。
1.4.2token方案
只要在頒發(fā)token時將頒發(fā)時間點和token時效一并設(shè)置到token中[1].就相當于將token時效信息內(nèi)嵌到了token自身。這不但合理利用了token攜帶信息的特性,也省去了額外的計時措施,降低了系統(tǒng)的復雜度。
1.5靈活配置接口的開放性
接口有兩種開放性,本系統(tǒng)中使用的是“攔截器+注解”。規(guī)定注解:@ AuthLogin標識用戶接口,其他沒有標注的都是通用接口。定義一個攔截器:Authenticationlnterceptor處理用戶認證的邏輯,判斷目標接口是否標注@ AuthLogin注解,若標注了,則攔截并認證。由此,變更某個接口的開放性,添加或取消該接口的注解即可。
2用戶接口的權(quán)限鑒別
本系統(tǒng)采用“攔截器+注解”的方式,可以靈活配置接口的權(quán)限。設(shè)置注解:@ Permlssion。設(shè)置攔截器:AuthorizationlnterceptorAuthorizationlnterceptor只攔截被注解@ Permission標注了的接口。
在攔截器中,獲取來訪者的角色,根據(jù)角色查詢到來訪者能訪問的所有資源,再對比當前接口是否在可訪問資源列表中,如果在,則放行,否則不能訪問。
3數(shù)據(jù)同步
3.1概述
本系統(tǒng)通過后端代碼調(diào)用學校教務(wù)系統(tǒng)的接口,拉取教務(wù)系統(tǒng)數(shù)據(jù)庫數(shù)據(jù),作為本系統(tǒng)的數(shù)據(jù)源,再結(jié)合前端的可交互式界面,達到真正意義上的一鍵導人數(shù)據(jù)。雖然一鍵導人數(shù)據(jù)方便、快捷,節(jié)省人力及時間,但是通過這種方法導人數(shù)據(jù)的方式通常需要兩個系統(tǒng),即數(shù)據(jù)源系統(tǒng)(教務(wù)系統(tǒng))和消費數(shù)據(jù)的系統(tǒng)(本排課系統(tǒng))。這種定制化的工作并不需要重復進行,除非兩個系統(tǒng)的數(shù)據(jù)存儲結(jié)構(gòu)發(fā)生變化,否則接口不會發(fā)生較大變化,因此,對接口的適配能達到接近“一勞永逸”的效果。
3.2同步機制
3.2.1數(shù)據(jù)存儲結(jié)構(gòu)
在數(shù)據(jù)同步的語境中,數(shù)據(jù)消費方的數(shù)據(jù)存儲結(jié)構(gòu)總是依賴數(shù)據(jù)生產(chǎn)方[2]。根據(jù)生產(chǎn)方的數(shù)據(jù)結(jié)構(gòu),在本系統(tǒng)中構(gòu)建兩個對應(yīng)的數(shù)據(jù)接收實體類和兩個數(shù)據(jù)存儲實體類(數(shù)據(jù)庫對象PO)。數(shù)據(jù)接收實體類字段與數(shù)據(jù)生產(chǎn)方的數(shù)據(jù)結(jié)構(gòu)完全一致,而數(shù)據(jù)存儲實體類則是根據(jù)本系統(tǒng)的情況定制的實體類。為了讓消費方的數(shù)據(jù)存儲結(jié)構(gòu)保持相對穩(wěn)定的狀態(tài),需要加一層數(shù)據(jù)接收實體類作為緩沖,這部分實體類只作為數(shù)據(jù)生產(chǎn)方的映射實體,每當數(shù)據(jù)生產(chǎn)方的數(shù)據(jù)結(jié)構(gòu)改變,對數(shù)據(jù)接收實體的修改是不會對本系統(tǒng)產(chǎn)生關(guān)鍵性改動的。雖然增加了一層,但本系統(tǒng)的數(shù)據(jù)存儲實體還是需要改變,即使如此,大部分的改變已經(jīng)被數(shù)據(jù)接收實體類層吸收了,存儲結(jié)構(gòu)做微調(diào)即可。
3.2.2一次拉取的數(shù)據(jù)量
由于拉取到的數(shù)據(jù)在持久化之前都需要在內(nèi)存中駐留一段時間,因此需要考慮數(shù)據(jù)量是否會超出進程的內(nèi)存空間大小。排課系統(tǒng)涉及數(shù)據(jù)量較大,一次拉取所有數(shù)據(jù)的方案是不可行的[3]。所以,可以采取不同數(shù)據(jù)依次分開同步的方式拉取數(shù)據(jù)。在同步一種數(shù)據(jù)時,可以先拉取數(shù)據(jù)的主鍵,再根據(jù)主鍵逐條拉取詳細數(shù)據(jù)[4]。經(jīng)測試,當JVM的最大堆內(nèi)存設(shè)置為128MB時,最大可以開辟10000000個整形變量,以一次性拉取所有學生的主鍵為例,內(nèi)存完全能夠承受。
3.2.3數(shù)據(jù)更新策略
要完成數(shù)據(jù)消費方的數(shù)據(jù)與數(shù)據(jù)生產(chǎn)方的數(shù)據(jù)同步,需要實現(xiàn)以下兩點[5]:尋找生產(chǎn)方和消費方數(shù)據(jù)的差集并消除雙方的差異:比對更新生產(chǎn)方和消費方都有的數(shù)據(jù)。項目組給消費方的數(shù)據(jù)庫待同步數(shù)據(jù)增加一個字段latest_sync,標識該數(shù)據(jù)是否是最新的。每次同步數(shù)據(jù)前,將表中的latest_sync字段置為0,表示數(shù)據(jù)都沒更新,然后拉取并遍歷生產(chǎn)方的數(shù)據(jù),逐個查找消費方的數(shù)據(jù)庫,是否存在數(shù)據(jù),若不存在,則說明該數(shù)據(jù)需要在消費方新增,并置lastest_sync字段為1,若存在,則比對更新,也置lastest_sync字段為1,如此遍歷完成后,所有l(wèi)astest_sync字段為0的數(shù)據(jù)就都是生產(chǎn)方?jīng)]有但消費方有的數(shù)據(jù),需要刪除。
4排課
4.1概述
排課問題主要有以下幾類實體:教師、上課教室、上課班級、授課課程。排課問題主要是要解決上述實體之間對資源利用的沖突。該問題的最終產(chǎn)出是教學課表,課表中的每一項大致可以分為某個時間段、某個教師、某個教室、某個班級、教授某門課程。
4.2排課約束條件
排課的約束條件主要來源于時間和空間上的限制。例如,同一個教室在同一個時間片只能有一場授課活動、同一個教師在同一個時間片只能在一個教室教同一個班級的課,同樣的,同一個班級在同一個時間片也只能在同一個教室上同一門課。排課系統(tǒng)的主要約束條件有以下幾個因素:日寸間片、教室、教師、課程和班級。為了使排課能夠順利進行,排課的所有因素必須滿足上述時空約束條件。
4.3排課的輸入
排課最核心的基礎(chǔ)數(shù)據(jù)是學期計劃表,每一個學期計劃表的每一行構(gòu)成了排課流程的主要輸入。計劃表規(guī)定了授課教師、授課班級、教授課程,計劃表的每一行包括該節(jié)課的課時數(shù)、上課人數(shù)、上課班級等。
4.4排課關(guān)鍵流程
本系統(tǒng)的排課算法采用遍歷算法。排課的核心任務(wù)就是,針對每個學期計劃表行,將人(教師、班級)安排到計劃表指定教室的某個時間片中,因此,排課過程實際要確定的是一個學期計劃表行的上課時間和上課地點,對于教師和班級條件都是在學期計劃表中規(guī)定好的。本系統(tǒng)以時間片作為遍歷的頂層因素,遍歷一個學期內(nèi)所有可以排課的時間片,以時間片為條件,查詢已經(jīng)排好的課表數(shù)據(jù),若沒有結(jié)果,則該時間片沒有被占用,可以繼續(xù)嵌套遍歷所有教室。以教室主鍵為查詢條件,查詢已經(jīng)排好的課表數(shù)據(jù),若沒有結(jié)果,則該教室在當前日寸間片沒有其他課程安排,該教室條件滿足,在遍歷教室的循環(huán)中依次檢查授課教師和授課班級在當前時間片、當前教室是否有其他課程安排。若上述教室、教師、班級都符合條件、不沖突,則完成了對一個學期計劃表行的排課,可以生成一條排課數(shù)據(jù)并將其持久化。上述循環(huán)結(jié)束后,所有計劃表都被安排完畢,算法結(jié)束。