Compare commits
No commits in common. "main" and "qi" have entirely different histories.
53
.drone.yml
53
.drone.yml
@ -1,53 +0,0 @@
|
|||||||
---
|
|
||||||
kind: pipeline
|
|
||||||
type: kubernetes
|
|
||||||
name: default
|
|
||||||
|
|
||||||
metadata:
|
|
||||||
labels:
|
|
||||||
pod-security.kubernetes.io/audit: privileged
|
|
||||||
|
|
||||||
services:
|
|
||||||
- name: docker daemon
|
|
||||||
image: docker:dind
|
|
||||||
privileged: true
|
|
||||||
environment:
|
|
||||||
DOCKER_TLS_CERTDIR: ""
|
|
||||||
when:
|
|
||||||
event:
|
|
||||||
- tag
|
|
||||||
- promote
|
|
||||||
|
|
||||||
steps:
|
|
||||||
- name: node.js build
|
|
||||||
image: node:18
|
|
||||||
commands:
|
|
||||||
- "npm add --global pnpm"
|
|
||||||
- pnpm i
|
|
||||||
- pnpm run build
|
|
||||||
|
|
||||||
- name: container build
|
|
||||||
image: docker:latest
|
|
||||||
privileged: true
|
|
||||||
commands:
|
|
||||||
- "while ! docker stats --no-stream; do sleep 1; done"
|
|
||||||
- "docker build -t $DOCKER_REGISTRY/glmdev/mathy ."
|
|
||||||
- "docker push $DOCKER_REGISTRY/glmdev/mathy"
|
|
||||||
environment:
|
|
||||||
DOCKER_HOST: tcp://localhost:2375
|
|
||||||
DOCKER_REGISTRY:
|
|
||||||
from_secret: DOCKER_REGISTRY
|
|
||||||
when:
|
|
||||||
event:
|
|
||||||
- tag
|
|
||||||
- promote
|
|
||||||
|
|
||||||
- name: k8s rollout
|
|
||||||
image: bitnami/kubectl
|
|
||||||
commands:
|
|
||||||
- cd deploy && kubectl apply -f .
|
|
||||||
- kubectl rollout -n mathy restart deployment/mathy
|
|
||||||
when:
|
|
||||||
event:
|
|
||||||
- tag
|
|
||||||
- promote
|
|
56
deploy.yaml
Normal file
56
deploy.yaml
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
apiVersion: apps/v1
|
||||||
|
kind: Deployment
|
||||||
|
metadata:
|
||||||
|
name: mathy
|
||||||
|
spec:
|
||||||
|
selector:
|
||||||
|
matchLabels:
|
||||||
|
name: mathy
|
||||||
|
template:
|
||||||
|
metadata:
|
||||||
|
labels:
|
||||||
|
name: mathy
|
||||||
|
spec:
|
||||||
|
containers:
|
||||||
|
- name: mathy
|
||||||
|
image: glmdev/mathy:latest
|
||||||
|
imagePullPolicy: Always
|
||||||
|
ports:
|
||||||
|
- containerPort: 80
|
||||||
|
---
|
||||||
|
apiVersion: v1
|
||||||
|
kind: Service
|
||||||
|
metadata:
|
||||||
|
name: mathy-service
|
||||||
|
spec:
|
||||||
|
ports:
|
||||||
|
- name: http
|
||||||
|
port: 80
|
||||||
|
protocol: TCP
|
||||||
|
targetPort: 80
|
||||||
|
selector:
|
||||||
|
name: mathy
|
||||||
|
---
|
||||||
|
apiVersion: networking.k8s.io/v1
|
||||||
|
kind: Ingress
|
||||||
|
metadata:
|
||||||
|
name: mathy-ingress
|
||||||
|
annotations:
|
||||||
|
kubernetes.io/ingress.class: "nginx"
|
||||||
|
nginx.ingress.kubernetes.io/ssl-redirect: "true"
|
||||||
|
spec:
|
||||||
|
tls:
|
||||||
|
- hosts:
|
||||||
|
- mathy.glmdev.tech
|
||||||
|
secretName: mathy-tls
|
||||||
|
rules:
|
||||||
|
- host: "mathy.glmdev.tech"
|
||||||
|
http:
|
||||||
|
paths:
|
||||||
|
- pathType: Prefix
|
||||||
|
path: "/"
|
||||||
|
backend:
|
||||||
|
service:
|
||||||
|
name: mathy-service
|
||||||
|
port:
|
||||||
|
number: 80
|
@ -1,5 +0,0 @@
|
|||||||
---
|
|
||||||
apiVersion: v1
|
|
||||||
kind: Namespace
|
|
||||||
metadata:
|
|
||||||
name: mathy
|
|
@ -1,12 +0,0 @@
|
|||||||
apiVersion: cert-manager.io/v1
|
|
||||||
kind: Certificate
|
|
||||||
metadata:
|
|
||||||
name: mathy-tls
|
|
||||||
namespace: mathy
|
|
||||||
spec:
|
|
||||||
secretName: mathy-tls
|
|
||||||
dnsNames:
|
|
||||||
- 'crystalmath.garrettmills.dev'
|
|
||||||
issuerRef:
|
|
||||||
name: letsencrypt-ca
|
|
||||||
kind: ClusterIssuer
|
|
@ -1,127 +0,0 @@
|
|||||||
---
|
|
||||||
apiVersion: apps/v1
|
|
||||||
kind: Deployment
|
|
||||||
metadata:
|
|
||||||
name: mathy
|
|
||||||
namespace: mathy
|
|
||||||
spec:
|
|
||||||
selector:
|
|
||||||
matchLabels:
|
|
||||||
name: mathy
|
|
||||||
template:
|
|
||||||
metadata:
|
|
||||||
labels:
|
|
||||||
name: mathy
|
|
||||||
spec:
|
|
||||||
containers:
|
|
||||||
- name: mathy
|
|
||||||
image: glmdev/mathy:latest
|
|
||||||
imagePullPolicy: Always
|
|
||||||
ports:
|
|
||||||
- containerPort: 80
|
|
||||||
---
|
|
||||||
apiVersion: apps/v1
|
|
||||||
kind: Deployment
|
|
||||||
metadata:
|
|
||||||
name: mathy-api
|
|
||||||
namespace: mathy
|
|
||||||
spec:
|
|
||||||
selector:
|
|
||||||
matchLabels:
|
|
||||||
name: mathy-api
|
|
||||||
template:
|
|
||||||
metadata:
|
|
||||||
labels:
|
|
||||||
name: mathy-api
|
|
||||||
spec:
|
|
||||||
containers:
|
|
||||||
- name: mathy
|
|
||||||
image: glmdev/mathy-api:latest
|
|
||||||
imagePullPolicy: Always
|
|
||||||
env:
|
|
||||||
- name: REDIS_HOST
|
|
||||||
value: localhost
|
|
||||||
- name: DATABASE_HOST
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: psql-conn
|
|
||||||
key: host
|
|
||||||
optional: false
|
|
||||||
- name: DATABASE_USERNAME
|
|
||||||
value: mathy
|
|
||||||
- name: DATABASE_PASSWORD
|
|
||||||
valueFrom:
|
|
||||||
secretKeyRef:
|
|
||||||
name: psql-conn
|
|
||||||
key: password
|
|
||||||
optional: false
|
|
||||||
- name: DATABASE_NAME
|
|
||||||
value: mathy
|
|
||||||
ports:
|
|
||||||
- containerPort: 8000
|
|
||||||
|
|
||||||
- name: redis
|
|
||||||
image: redis:latest
|
|
||||||
imagePullPolicy: Always
|
|
||||||
ports:
|
|
||||||
- containerPort: 6379
|
|
||||||
---
|
|
||||||
apiVersion: v1
|
|
||||||
kind: Service
|
|
||||||
metadata:
|
|
||||||
name: mathy-api-service
|
|
||||||
namespace: mathy
|
|
||||||
spec:
|
|
||||||
ports:
|
|
||||||
- name: http
|
|
||||||
port: 80
|
|
||||||
protocol: TCP
|
|
||||||
targetPort: 8000
|
|
||||||
selector:
|
|
||||||
name: mathy-api
|
|
||||||
---
|
|
||||||
apiVersion: v1
|
|
||||||
kind: Service
|
|
||||||
metadata:
|
|
||||||
name: mathy-service
|
|
||||||
namespace: mathy
|
|
||||||
spec:
|
|
||||||
ports:
|
|
||||||
- name: http
|
|
||||||
port: 80
|
|
||||||
protocol: TCP
|
|
||||||
targetPort: 80
|
|
||||||
selector:
|
|
||||||
name: mathy
|
|
||||||
---
|
|
||||||
apiVersion: networking.k8s.io/v1
|
|
||||||
kind: Ingress
|
|
||||||
metadata:
|
|
||||||
name: mathy-ingress
|
|
||||||
namespace: mathy
|
|
||||||
annotations:
|
|
||||||
kubernetes.io/ingress.class: "nginx"
|
|
||||||
nginx.ingress.kubernetes.io/ssl-redirect: "true"
|
|
||||||
spec:
|
|
||||||
tls:
|
|
||||||
- hosts:
|
|
||||||
- crystalmath.garrettmills.dev
|
|
||||||
secretName: mathy-tls
|
|
||||||
rules:
|
|
||||||
- host: "crystalmath.garrettmills.dev"
|
|
||||||
http:
|
|
||||||
paths:
|
|
||||||
- pathType: Prefix
|
|
||||||
path: "/api"
|
|
||||||
backend:
|
|
||||||
service:
|
|
||||||
name: mathy-api-service
|
|
||||||
port:
|
|
||||||
number: 80
|
|
||||||
- pathType: Prefix
|
|
||||||
path: "/"
|
|
||||||
backend:
|
|
||||||
service:
|
|
||||||
name: mathy-service
|
|
||||||
port:
|
|
||||||
number: 80
|
|
@ -9,10 +9,10 @@
|
|||||||
"lint": "eslint . --ext .ts",
|
"lint": "eslint . --ext .ts",
|
||||||
"lint:fix": "eslint --fix . --ext .ts",
|
"lint:fix": "eslint --fix . --ext .ts",
|
||||||
"preview": "vite preview",
|
"preview": "vite preview",
|
||||||
"cd:build": "pnpm run build && docker image build . -t ${DOCKER_REGISTRY}/glmdev/mathy",
|
"cd:build": "pnpm run build && docker image build . -t glmdev/mathy",
|
||||||
"cd:push": "docker push ${DOCKER_REGISTRY}/glmdev/mathy",
|
"cd:push": "docker push glmdev/mathy",
|
||||||
"cd:deploy": "kubectl apply -f deploy/1-certificate.yaml -f deploy/2-deploy.yaml",
|
"cd:deploy": "kubectl apply -f deploy.yaml",
|
||||||
"cd:rollout": "kubectl rollout -n mathy restart deployment/mathy",
|
"cd:rollout": "kubectl rollout restart deployment/mathy",
|
||||||
"cd": "pnpm run cd:build && pnpm run cd:push && pnpm run cd:rollout"
|
"cd": "pnpm run cd:build && pnpm run cd:push && pnpm run cd:rollout"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
|
@ -3,11 +3,10 @@ import * as math from 'mathjs'
|
|||||||
import { v4 as uuidv4 } from 'uuid'
|
import { v4 as uuidv4 } from 'uuid'
|
||||||
import { LineChart } from 'vue-chart-3'
|
import { LineChart } from 'vue-chart-3'
|
||||||
import { computed, ref } from 'vue'
|
import { computed, ref } from 'vue'
|
||||||
import { Chart, ChartData, registerables } from 'chart.js'
|
import { Chart, ChartData, ChartOptions, registerables } from 'chart.js'
|
||||||
import { MathStatement } from '../support/parse'
|
import { MathStatement } from '../support/parse'
|
||||||
import { ChartBox } from '../support/types'
|
import { ChartBox } from '../support/types'
|
||||||
import { stepX, stepY } from '../support/const'
|
import { stepX, stepY } from '../support/const'
|
||||||
import {MathPage} from '../support/page'
|
|
||||||
|
|
||||||
Chart.register(...registerables)
|
Chart.register(...registerables)
|
||||||
|
|
||||||
@ -18,7 +17,6 @@ const emit = defineEmits<{
|
|||||||
}>()
|
}>()
|
||||||
|
|
||||||
const props = defineProps<{
|
const props = defineProps<{
|
||||||
page: MathPage,
|
|
||||||
fn: MathStatement,
|
fn: MathStatement,
|
||||||
value: ChartBox,
|
value: ChartBox,
|
||||||
}>()
|
}>()
|
||||||
@ -71,33 +69,27 @@ const getChartData = (): ChartData<'line'> => {
|
|||||||
throw new TypeError('Cannot chart node that is not a function.')
|
throw new TypeError('Cannot chart node that is not a function.')
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
|
||||||
const evaluationResult = props.page.evaluate()
|
|
||||||
const node = props.fn.parse() as math.FunctionAssignmentNode
|
const node = props.fn.parse() as math.FunctionAssignmentNode
|
||||||
const fn = node.compile().evaluate(evaluationResult.scope)
|
const fn = node.compile().evaluate() // FIXME need dependencies in scope
|
||||||
|
|
||||||
|
console.log('getChartData', {
|
||||||
|
labels: range.map(x => `${x}`),
|
||||||
|
datasets: [
|
||||||
|
{
|
||||||
|
label: node.name,
|
||||||
|
data: range.map(n => fn(n)),
|
||||||
|
},
|
||||||
|
],
|
||||||
|
})
|
||||||
return {
|
return {
|
||||||
labels: range.map(x => `${x}`),
|
labels: range.map(x => `${x}`),
|
||||||
datasets: [{
|
datasets: [{
|
||||||
label: node.name,
|
label: node.name,
|
||||||
backgroundColor: '#553564',
|
backgroundColor: '#553564',
|
||||||
borderColor: '#ccc',
|
|
||||||
data: range.map(x => fn(x)),
|
data: range.map(x => fn(x)),
|
||||||
pointRadius: 5
|
pointRadius: 5
|
||||||
}],
|
}],
|
||||||
}
|
}
|
||||||
} catch (_) {
|
|
||||||
return {
|
|
||||||
labels: [],
|
|
||||||
datasets: [{
|
|
||||||
label: '',
|
|
||||||
backgroundColor: '#553564',
|
|
||||||
borderColor: '#ccc',
|
|
||||||
data: [],
|
|
||||||
pointRadius: 5
|
|
||||||
}],
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const chartData = ref(getChartData())
|
const chartData = ref(getChartData())
|
||||||
|
@ -103,7 +103,6 @@ const openEditFunctionModal = () => {
|
|||||||
editFunctionModalOpen.value = true
|
editFunctionModalOpen.value = true
|
||||||
}
|
}
|
||||||
|
|
||||||
const chartBoxKey = ref(uuidv4())
|
|
||||||
const updateStatements = () => {
|
const updateStatements = () => {
|
||||||
statements.value = math.value.getStatements();
|
statements.value = math.value.getStatements();
|
||||||
try {
|
try {
|
||||||
@ -154,21 +153,18 @@ const saveNewVariable = (stmt: MathStatement) => {
|
|||||||
math.value.addStatement(stmt)
|
math.value.addStatement(stmt)
|
||||||
newVariableModalOpen.value = false
|
newVariableModalOpen.value = false
|
||||||
updateStatements()
|
updateStatements()
|
||||||
chartBoxKey.value = uuidv4()
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const saveNewExpression = (stmt: MathStatement) => {
|
const saveNewExpression = (stmt: MathStatement) => {
|
||||||
math.value.addStatement(stmt)
|
math.value.addStatement(stmt)
|
||||||
newExpressionModalOpen.value = false
|
newExpressionModalOpen.value = false
|
||||||
updateStatements()
|
updateStatements()
|
||||||
chartBoxKey.value = uuidv4()
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const saveNewFunction = (stmt: MathStatement) => {
|
const saveNewFunction = (stmt: MathStatement) => {
|
||||||
math.value.addStatement(stmt)
|
math.value.addStatement(stmt)
|
||||||
newFunctionModalOpen.value = false
|
newFunctionModalOpen.value = false
|
||||||
updateStatements()
|
updateStatements()
|
||||||
chartBoxKey.value = uuidv4()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const editStatement = (stmt: MathStatement) => {
|
const editStatement = (stmt: MathStatement) => {
|
||||||
@ -186,7 +182,6 @@ const editStatement = (stmt: MathStatement) => {
|
|||||||
const removeStatement = (stmt: MathStatement) => {
|
const removeStatement = (stmt: MathStatement) => {
|
||||||
math.value.removeStatement(stmt.id)
|
math.value.removeStatement(stmt.id)
|
||||||
updateStatements()
|
updateStatements()
|
||||||
chartBoxKey.value = uuidv4()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const finishEditStatement = () => {
|
const finishEditStatement = () => {
|
||||||
@ -194,7 +189,6 @@ const finishEditStatement = () => {
|
|||||||
editVarDeclModalOpen.value = false
|
editVarDeclModalOpen.value = false
|
||||||
editFunctionModalOpen.value = false
|
editFunctionModalOpen.value = false
|
||||||
updateStatements()
|
updateStatements()
|
||||||
chartBoxKey.value = uuidv4()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -208,6 +202,7 @@ const makeNewRichTextBox = () => {
|
|||||||
richEditModal.value = true;
|
richEditModal.value = true;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const chartBoxKey = ref(uuidv4())
|
||||||
const chartBoxes = ref<ChartBox[]>([])
|
const chartBoxes = ref<ChartBox[]>([])
|
||||||
|
|
||||||
const newChartModalOpen = ref(false)
|
const newChartModalOpen = ref(false)
|
||||||
@ -218,7 +213,6 @@ const openNewChartModal = () => {
|
|||||||
const saveNewChartBox = (chartBox: ChartBox) => {
|
const saveNewChartBox = (chartBox: ChartBox) => {
|
||||||
chartBoxes.value.push(chartBox)
|
chartBoxes.value.push(chartBox)
|
||||||
newChartModalOpen.value = false
|
newChartModalOpen.value = false
|
||||||
chartBoxKey.value = uuidv4()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const editingChartBox = ref<ChartBox | undefined>()
|
const editingChartBox = ref<ChartBox | undefined>()
|
||||||
@ -277,7 +271,7 @@ const removeRichTextBox = (id: number) => {
|
|||||||
const makeNewImageBox = () => {
|
const makeNewImageBox = () => {
|
||||||
images.value.push(new ImageContainer(''));
|
images.value.push(new ImageContainer(''));
|
||||||
imageID.value = images.value.length - 1;
|
imageID.value = images.value.length - 1;
|
||||||
imageURL.value = images.value[imageID.value].url;
|
imageURL.value = images.value[richEditID.value].url;
|
||||||
imageModal.value = true;
|
imageModal.value = true;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -368,12 +362,9 @@ const saveEditorPage = async (close = false) => {
|
|||||||
return alert('Failed to save page: ' + result.message)
|
return alert('Failed to save page: ' + result.message)
|
||||||
}
|
}
|
||||||
|
|
||||||
const justCreated = !editorPageId.value
|
|
||||||
editorPageId.value = result.data.pageId
|
editorPageId.value = result.data.pageId
|
||||||
if ( close ) {
|
if ( close ) {
|
||||||
await router.push('/Listings')
|
await router.push('/Listings')
|
||||||
} else if ( justCreated ) {
|
|
||||||
await router.push(`/Editor/${editorPageId.value}`)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -524,7 +515,6 @@ onMounted(() => {
|
|||||||
<q-page-container id="editor" style='padding: 0'>
|
<q-page-container id="editor" style='padding: 0'>
|
||||||
<span v-for="(chartBox, index) in chartBoxes" style="display: flex">
|
<span v-for="(chartBox, index) in chartBoxes" style="display: flex">
|
||||||
<RangeChart
|
<RangeChart
|
||||||
:page="math"
|
|
||||||
:fn="math.getFunctionByNameOrFail(chartBox.fnName)"
|
:fn="math.getFunctionByNameOrFail(chartBox.fnName)"
|
||||||
:key="chartBoxKey"
|
:key="chartBoxKey"
|
||||||
:value="chartBox"
|
:value="chartBox"
|
||||||
|
@ -197,7 +197,6 @@ export class MathPage {
|
|||||||
return {
|
return {
|
||||||
variables: nonFunctionalScope,
|
variables: nonFunctionalScope,
|
||||||
statements: evaluations,
|
statements: evaluations,
|
||||||
scope,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -90,7 +90,6 @@ export type EvaluatedValue = TypeTag<'@app.EvaluatedValue'> & string
|
|||||||
export interface EvaluationResult {
|
export interface EvaluationResult {
|
||||||
variables: Record<VariableName, any>
|
variables: Record<VariableName, any>
|
||||||
statements: Record<StatementID, any>
|
statements: Record<StatementID, any>
|
||||||
scope: Record<VariableName, any>
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user