Skip to content

Commit 714bc70

Browse files
Add CORS (#277)
1 parent a308de7 commit 714bc70

File tree

13 files changed

+185
-55
lines changed

13 files changed

+185
-55
lines changed
File renamed without changes.

dev_v2.md renamed to dev.md

Lines changed: 26 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ The **Montage Project** is a web application with two main components:
1717
- Built with **Clastic**, a Python framework.
1818
- Uses various Python libraries such as:
1919
- **SQLAlchemy**: Database interactions.
20-
- **mwoauth**: Used for authentication with MediaWikis OAuth.
20+
- **mwoauth**: Used for authentication with MediaWiki's OAuth.
2121
- **pymysql**: MySQL driver.
2222
- Serves the frontend and exposes API endpoints for application functionality.
2323

@@ -40,20 +40,32 @@ git clone [email protected]:hatnote/montage.git
4040
cd montage
4141
```
4242

43-
### 2. Start the Frontend Build Watcher
43+
### 2. Set up the Frontend
4444
```bash
4545
cd frontend
4646
npm install
47-
npm run watch:build
4847
```
4948

50-
⚠️ **Frontend does not run in dev mode**: `npm run watch:build` above will watch for changes by using `chokidar` command and automatically copied to the backend's `static` and `template` directories. So there will not be any hot reloading. Developers must refresh the browser to see updates.
49+
### 3. Configure Environment Variables
50+
```bash
51+
cp .env.default .env
52+
```
53+
54+
Edit the `.env` file to match your development environment. By default, it's configured to connect to a locally running backend at `http://localhost:5001`.
55+
56+
### 4. Run the Frontend in Development Mode
57+
```bash
58+
npm run dev
59+
```
60+
61+
This will start the Vite development server with hot module replacement.
5162

52-
Apart from `npm watch:build`, these are other commands:
63+
Other frontend development commands:
64+
* `npm run build`: Build for production
5365
* `npm run lint`: Lint the code
5466
* `npm run format`: Format the code
5567

56-
### 3. Use the Makefile to start the backend
68+
### 5. Use the Makefile to start the backend
5769
* Open a new terminal tab and change directory to root of repo
5870
* Copy and edit `config.dev.yaml` based on `config.default.yaml`
5971
* (Optional) In `config.dev.yaml` there is a line for `dev_local_cookie_value`. To get it,
@@ -76,15 +88,16 @@ This will build the docker image for the montage backend and start the container
7688
* `make logs` : Stream the backend container logs in real-time.
7789
* `make restart` : Restart the backend container
7890

79-
### 4. Access the Application
80-
* Open http://localhost:5001 in your browser.
91+
### 6. Access the Application
92+
* With development server: Open http://localhost:5173 in your browser (frontend)
93+
* With backend serving frontend: Open http://localhost:5001 in your browser
8194

8295
The application server runs on localhost port 5001, visit [http://localhost:5001/meta](http://localhost:5001/meta) to see a list
8396
of valid URL patterns and other details.
8497

8598
Almost all endpoints from backend (except for OAuth and `/static/`) return JSON as long as the proper Accept header is set (done by most libraries) or `format=json` is passed in the query string.
8699

87-
## Project struture (v2 only)
100+
## Project structure
88101
```bash
89102
├── DEV.md
90103
├── Dockerfile
@@ -105,6 +118,8 @@ Almost all endpoints from backend (except for OAuth and `/static/`) return JSON
105118
│   ├── jsconfig.json
106119
│   ├── package-lock.json
107120
│   ├── package.json
121+
│ ├── .env.default
122+
│ ├── .env
108123
│   ├── public
109124
│   ├── src
110125
│   └── vite.config.js
@@ -184,6 +199,8 @@ These provides a detailed explanation of the main components in the **Montage Pr
184199
- **`src/`**: Source code, including components, routes, and utilities.
185200
- **`public/`**: Static assets, such as images and global styles.
186201
- **`vite.config.js`**: Configuration for the Vite build tool.
202+
- **`.env.default`**: Template for environment configuration.
203+
- **`.env`**: Local environment configuration.
187204

188205

189206
#### Directory: `tools`

frontend/.env.default

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
VITE_API_ENDPOINT=http://localhost:5001

frontend/package.json

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@
77
"dev": "vite",
88
"build": "vite build",
99
"preview": "vite preview",
10-
"watch:build": "chokidar 'src/**/*' -c 'npm run build && cp -r dist/* ../montage/static' --initial",
1110
"toolforge:build": "export SHELL=/bin/sh && npm run build && cp -r dist/* ../montage/static",
1211
"lint": "eslint . --ext .vue,.js,.jsx,.cjs,.mjs --fix --ignore-path .gitignore",
1312
"format": "prettier --write src/"

frontend/src/components/Campaign/AllCampaign.vue

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -61,9 +61,9 @@ onMounted(() => {
6161
6262
// Order campaigns by open date (more recent at the top)
6363
coordinatorCampaigns.value.sort((campaign1, campaign2) => {
64-
if (campaign1.open_date === campaign2.open_date) {
64+
if (campaign1.create_date === campaign2.create_date) {
6565
return 0
66-
} else if (campaign1.open_date < campaign2.open_date) {
66+
} else if (campaign1.create_date < campaign2.create_date) {
6767
return 1
6868
} else {
6969
return -1

frontend/src/i18n.js

Lines changed: 15 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1,40 +1,33 @@
11
import { createI18n } from 'vue-i18n';
22
import en from '@/i18n/en.json';
33

4-
// Initialize with default English messages in case of error
5-
const messages = { en };
4+
const messages = { en };
65

7-
// Dynamically load all other messages
8-
async function loadMessages() {
6+
const i18n = createI18n({
7+
legacy: false,
8+
locale: 'en',
9+
fallbackLocale: 'en',
10+
messages
11+
});
12+
13+
// Dynamically load additional messages after initialization
14+
const loadMessages = async () => {
915
try {
1016
const modules = import.meta.glob('./i18n/*.json');
1117
await Promise.all(
1218
Object.entries(modules).map(async ([path, importFn]) => {
1319
const lang = path.replace('./i18n/', '').replace('.json', '');
1420
if (lang !== 'en' && lang !== 'qqq') {
1521
const module = await importFn();
16-
messages[lang] = module.default;
22+
i18n.global.setLocaleMessage(lang, module.default);
1723
}
1824
})
1925
);
26+
return i18n;
2027
} catch (error) {
2128
console.error('Error loading i18n messages:', error);
29+
return i18n;
2230
}
23-
}
24-
25-
// Initialize i18n instance
26-
async function initializeI18n() {
27-
try {
28-
await loadMessages();
29-
} catch (error) {
30-
console.error('Error initializing i18n:', error);
31-
}
32-
33-
return createI18n({
34-
locale: 'en',
35-
fallbackLocale: 'en',
36-
messages
37-
});
38-
}
31+
};
3932

40-
export default initializeI18n;
33+
export { i18n, loadMessages };

frontend/src/main.js

Lines changed: 15 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ import { createPinia } from 'pinia'
33

44
import App from './App.vue'
55
import router from './router'
6-
import initializeI18n from './i18n'
6+
import { i18n, loadMessages } from './i18n'
77
import Toast from 'vue-toastification'
88
import 'vue-toastification/dist/index.css'
99

@@ -13,21 +13,21 @@ import ClipLoader from 'vue-spinner/src/ClipLoader.vue'
1313
import DatePicker from 'vue-datepicker-next'
1414
import 'vue-datepicker-next/index.css'
1515

16-
(async () => {
17-
// Wait for i18n initialization
18-
const i18n = await initializeI18n()
19-
const app = createApp(App)
16+
const app = createApp(App)
2017

21-
app.use(createPinia())
22-
app.use(router)
23-
app.use(Toast)
24-
app.use(i18n)
18+
app.use(createPinia())
19+
app.use(router)
20+
app.use(Toast)
21+
app.use(i18n) // Use i18n immediately with English locale
2522

26-
// Global directive
27-
app.directive('tooltip', CdxTooltip)
28-
app.component('clip-loader', ClipLoader)
23+
// Global directive
24+
app.directive('tooltip', CdxTooltip)
25+
app.component('clip-loader', ClipLoader)
26+
app.component('date-picker', DatePicker)
2927

30-
app.component('date-picker', DatePicker)
28+
app.mount('#app')
3129

32-
app.mount('#app')
33-
})()
30+
// Load additional language messages dynamically
31+
loadMessages().then(() => {
32+
console.log('All language messages loaded');
33+
});

frontend/src/services/api.js

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,12 @@ import { useLoadingStore } from '@/stores/loading'
33

44
// Create Axios instance for Backend API
55
const apiBackend = axios.create({
6-
baseURL: '/v1/',
6+
baseURL: import.meta.env.VITE_API_ENDPOINT + '/v1/',
77
headers: {
88
'Content-Type': 'application/json',
99
Accept: 'application/json'
10-
}
10+
},
11+
withCredentials: true
1112
})
1213

1314
// Create Axios instance for Commons API

frontend/src/stores/user.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,14 +9,14 @@ export const useUserStore = defineStore('user-store', () => {
99

1010
function login(userObj) {
1111
if (!userObj) {
12-
window.location = window.location.origin + '/login'
12+
window.location = import.meta.env.VITE_API_ENDPOINT + '/login'
1313
}
1414
user.value = userObj
1515
isAuthenticated.value = true
1616
}
1717

1818
function logout() {
19-
window.location = window.location.origin + '/logout'
19+
window.location = import.meta.env.VITE_API_ENDPOINT + '/logout'
2020
user.value = null
2121
isAuthenticated.value = false
2222
authChecked.value = true

frontend/vite.config.js

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,5 +12,8 @@ export default defineConfig({
1212
alias: {
1313
'@': fileURLToPath(new URL('./src', import.meta.url))
1414
}
15+
},
16+
server: {
17+
port: 5173,
1518
}
1619
})

0 commit comments

Comments
 (0)