196 Commits
Author SHA1 Message Date
didier 95a8ed5ffa added the worst kind of security ever 2024-07-02 19:43:24 -04:00
didier cd45813228 fixed type 2024-07-02 19:22:51 -04:00
didier a31390d55a prepared for migration 2024-07-02 19:01:57 -04:00
didier.amyot df26a3fe96 Added new website 2024-07-02 18:36:05 -04:00
didier.amyot 293b7727e2 deleted old website. fuck it. 2024-07-02 18:35:00 -04:00
didier ce4f47b79c added more scores 2024-06-29 19:09:02 -04:00
didier e874c125ea boom 2024-06-19 07:46:42 -04:00
didier amyot ae180fc3c8 added results 2024-05-13 20:49:21 -04:00
didier amyot 65c9da0a1d added new season 2024-05-13 20:32:31 -04:00
didier amyot 32d5666c4e fixed little bug. 2023-08-27 12:48:55 +00:00
Cameron Letourneau f853ccd820 Update resultats2023.yaml 2023-08-25 12:30:24 +00:00
Cameron Letourneau 297aa5c3b0 Update resultats2023.yaml 2023-08-18 14:58:02 +00:00
Cameron Letourneau da556a5d25 Update resultats2023.yaml 2023-08-18 14:33:30 +00:00
didier amyot ac05980fad modified jour-de-la-balle 2023-08-07 18:27:14 -04:00
didier amyot 593ed01669 updated jour-de-la-balle 2023-08-05 10:58:41 -04:00
didier amyot 8393749900 added one game for la fete de la balle 2023-08-01 10:39:50 -04:00
Cameron Letourneau 12676278c1 Update resultats2023.yaml 2023-07-28 13:46:36 +00:00
didier amyot 016d629aed adeed new game 2023-07-25 10:29:18 -04:00
didier amyot 1ebf5dc2d0 Added new scores 2023-07-21 09:28:03 -04:00
Cameron Letourneau ad5f3c0a67 Update resultats2023.yaml 2023-07-14 13:28:00 +00:00
didier amyot 89899d82b8 forgotten to add file 2023-07-12 16:57:13 -04:00
didier amyot 3c505d7d5e fixed small bug 2023-07-12 16:54:49 -04:00
Cameron Letourneau 250fe56322 Update pour article 2023 2023-07-09 16:22:12 +00:00
Cameron Letourneau 958ccaf246 Add new file 2023-07-09 16:16:03 +00:00
Cameron Letourneau c6cba8ef62 Update resultats2023.yaml 2023-07-08 17:09:48 +00:00
Cameron Letourneau 87d6b9667a Update resultats2023.yaml 2023-06-30 13:59:53 +00:00
Cameron Letourneau 19fa311496 Update resultats2023.yaml 2023-06-24 13:15:38 +00:00
Cameron Letourneau e19a7c5c68 Update resultats2023.yaml 2023-06-23 19:53:20 +00:00
Cameron Letourneau a1bec8a62b Update resultats2023.yaml 2023-06-09 09:53:38 +00:00
Cameron Letourneau 795d9d4099 Update resultats2023.yaml 2023-06-02 23:56:25 +00:00
Cameron Letourneau cc1dd3d652 Merge branch 'master' into 'master'
Update file resultats2023.yaml

See merge request ballephenix/website!1
2023-06-02 23:54:56 +00:00
Cameron Letourneau 51eb6d1ebb Update file resultats2023.yaml 2023-06-02 23:09:06 +00:00
didier amyot cf2de58a77 added updated schedule 2023-06-01 13:19:06 -04:00
didier amyot 05897534c8 Updated games 2023-06-01 13:07:17 -04:00
didier amyot c472aac40b fixed time in 2023 result file 2023-05-22 11:41:36 -04:00
didier amyot 257fc4e630 changed results and schedule of 2023 season. 2023-05-22 11:19:35 -04:00
didier amyot 978d4dd6b1 fixed plurialization typo from 'gri' to 'gris' 2023-05-02 14:37:19 -04:00
didier amyot e58239e6b9 Rename yaml file extension from yml to yaml to make it work with build system 2023-05-02 14:32:39 -04:00
didier amyot f68b91602d added 2023 schedule 2023-05-02 13:45:14 -04:00
didier amyot bdb6b24da7 nsdds 2022-07-19 18:19:58 -04:00
didier amyot e42d42189c added more games 2022-07-04 20:32:20 -04:00
didier amyot 4aef8a9e84 no rain tomorrow 2022-06-29 17:43:15 -04:00
didier amyot e5916dcd21 calisse 2022-06-28 20:08:32 -04:00
didier amyot cf23f25af7 ostie d'or 2022-06-28 20:01:41 -04:00
didier amyot 9f8386af74 added more results 2022-06-11 18:45:12 -04:00
didier amyot 10950b4f50 fixed shit 2022-05-28 14:02:19 -04:00
didier amyot 29a7b9c078 added results 2022-05-28 13:56:08 -04:00
didier amyot 6efd4b8afd added y2k22 2022-05-28 13:52:03 -04:00
didier amyot 1e18870715 added basic nix flake file. 2022-05-28 13:18:13 -04:00
didier amyot a65de2a03a Update resultats2021.yaml 2021-07-30 13:35:05 +00:00
didier amyot fb83d95e7e Update resultats2021.yaml 2021-07-23 12:32:32 +00:00
didier amyot b5e1bf6cb0 Update resultats2021.yaml 2021-07-16 01:43:08 +00:00
didier amyot 375c2551fc changed files 2021-06-20 13:06:09 -04:00
didier amyot 0751d3e447 Update resultats2021.yaml 2021-06-16 00:17:41 +00:00
didier amyot 8897e9ac53 Update resultats2021.yaml 2021-06-16 00:14:45 +00:00
didier amyot 1f569b6f3d fixed contacts 2021-06-15 20:04:49 -04:00
didier amyot e18a393c9e fixed facebook link 2021-06-15 18:43:37 -04:00
didier amyot 7d21d5316b more love 2021-06-15 17:25:43 -04:00
didier amyot 548d4c1def added some support for practices 2021-06-15 16:55:21 -04:00
didier amyot 2f7dcdc5d0 added saison 2021 data 2021-06-15 16:18:03 -04:00
didier amyot 80ddf2b010 more love 2021-06-15 12:50:49 -04:00
didier amyot 9cabb7c2cd Given some love to the website 2021-06-15 12:45:21 -04:00
didier amyot 2916077329 Update rulesPage.js 2019-10-28 19:42:22 +00:00
didier amyot 7cfb302634 nkjnfdsk 2019-08-22 08:09:54 -04:00
didier amyot fb4b893e39 jdsk 2019-08-22 08:02:47 -04:00
didier amyot 19b7afa7c5 changed calendar 2019-08-06 15:21:15 -04:00
didier amyot 71e1491683 added more results 2019-08-01 17:14:06 -04:00
didier amyot 093370d199 blah 2019-07-13 09:49:50 -04:00
didier amyot d293b8be06 more points 2019-06-28 16:35:31 -04:00
didier amyot 161e828fe4 balh 2019-06-24 18:28:01 -04:00
didier amyot f84d375785 ajouter les reprises 2019-06-12 17:08:38 -04:00
didier amyot 8074b3679e added new score 2019-06-09 09:41:48 -04:00
didier amyot 75ecc7c346 added new scores 2019-06-03 15:36:00 -04:00
didier amyot 6c81a9aeb1 add rain for todays games 2019-05-16 14:20:21 -04:00
didier amyot 39cde030dd fixed away/home 2019-05-16 09:34:57 -04:00
didier amyot 6da40dfb6e added new game dates 2019-05-13 09:13:08 -04:00
didier amyot e93e54df8e nouvelle nouvelle 2019-04-01 08:09:36 -04:00
didier amyot 63cbf51af8 fixed pdf 2019-03-09 07:30:31 -05:00
didier amyot b634723762 removed unused download button 2019-03-09 07:00:21 -05:00
didier amyot cee0e920c3 Added previous seasons to the web site 2019-03-08 12:15:51 -05:00
didier amyot da7951b1cb fixed inscrition 2019 files 2019-03-05 21:40:54 +00:00
didier amyot 516a9856c1 changed main message 2019-02-20 09:20:32 -05:00
didier amyot 441b617eb1 changed some rules 2019-02-19 12:46:59 -05:00
didier amyot e343cee701 changed rules order 2019-02-17 20:20:14 -05:00
didier amyot fe69c01c10 fixed typo 2019-02-17 20:16:01 -05:00
didier amyot e421930f8b added documents for new commity 2019-02-17 20:10:40 -05:00
didier amyot 17f3103144 typo 2018-08-28 18:56:43 -04:00
didier amyot 3c81297272 added last game 2018-08-28 18:52:57 -04:00
didier amyot 25d2fdb781 Update resultats.yaml 2018-08-24 23:32:46 +00:00
didier amyot 42341dec3e Update resultats.yaml 2018-08-16 00:10:06 +00:00
didier amyot fdfef069cb added new score 2018-08-07 20:50:13 -04:00
didier amyot 8066c990cc new article 2018-07-09 20:19:38 -04:00
didier amyot 6118ae35ee Update resultats.yaml 2018-06-10 13:00:20 +00:00
didier amyot 223932df0a let's encrypt 2018-06-09 09:09:46 -04:00
didier amyot a10d01c8d7 added let's encrypt challenge 2018-06-09 09:02:50 -04:00
didier amyot f04c039e8c Update resultats.yaml 2018-06-05 23:33:44 +00:00
didier amyot 48377dbe9d Update resultats.yaml 2018-06-05 22:56:53 +00:00
didier amyot 8e4eb803d7 more resilient team structure 2018-05-20 17:12:57 -04:00
didier amyot 01bdcbe3b7 je suis saoul 2018-05-19 19:53:04 -04:00
didier amyot 6b2a781378 changed hour of the very first game 2018-05-16 20:41:58 -04:00
didier amyot e5bd620c88 created a 'remplaçants' team 2018-05-13 18:14:19 -04:00
didier amyot 3182c82dba changed team colour 2018-05-13 17:46:12 -04:00
didier amyot 26b09a0941 added evaluation 2018 2018-05-07 20:34:20 -04:00
didier amyot 926c35466d replace team strings 2018-05-04 14:18:34 -04:00
didier amyot 9cec9e101a added 2018 schedule 2018-05-04 14:15:42 -04:00
didier amyot 3d344de012 added enrollement for 2018 2018-03-19 17:40:12 -04:00
didier amyot bb6638ae79 added let's encrypt challenge 2018-03-11 15:39:50 -04:00
didier amyot 2f6b62afef added new article 2017-09-17 11:29:34 -04:00
didier amyot 6015d479fb Update resultats.yaml 2017-08-25 02:50:48 +00:00
didier amyot 9220f4d4a6 new message 2017-08-23 19:13:01 -04:00
didier amyot d8a655bd9b Update resultats.yaml 2017-08-23 01:05:19 +00:00
didier amyot c577d12fc1 oups 2017-08-19 18:48:51 -04:00
didier amyot 42a37856d2 applied richard's comments 2017-08-19 18:42:06 -04:00
didier amyot d085eeb91b Update resultats.yaml 2017-08-19 17:11:23 +00:00
didier amyot f3dcddcbc0 Update resultats.yaml 2017-08-19 17:00:14 +00:00
didier amyot 3dab44623a Update resultats.yaml 2017-08-18 13:43:52 +00:00
didier amyot 44eb09100c added new result 2017-08-09 21:24:48 -04:00
didier amyot deaf5f0fbc boom 2017-08-09 20:59:19 -04:00
didier amyot 9bf4830f7a added basic playoff integration 2017-08-08 22:22:51 -04:00
didier amyot 7be88a2167 Update resultats.yaml 2017-08-01 01:02:14 +00:00
didier amyot 4ef7661371 Update resultats.yaml 2017-07-23 15:25:43 +00:00
didier amyot 8ad11a2a78 trying to fix a prod issue 2017-07-17 22:00:38 -04:00
didier amyot 3d4995e228 Update resultats.yaml 2017-07-18 01:35:27 +00:00
didier amyot a46e4a463e added new scores 2017-07-09 18:00:18 -04:00
didier amyot b9c6612fb1 new results 2017-07-01 08:29:52 -04:00
didier amyot 4af9f56707 walter-stewart!!! 2017-06-20 20:57:25 -04:00
didier amyot 314a816fbd implemented comments and suggestions by marc beaudoin 2017-06-15 20:15:36 -04:00
didier amyot 3caa916d47 Update resultats.yaml 2017-06-05 23:31:10 +00:00
Valerie Andre fff837b103 correction inversion équipe home et away 2017-05-29 20:58:06 -04:00
Valerie Andre f9893f3130 updates dates et ordre des matchs 2017-05-29 20:39:55 -04:00
didier amyot 334c40dead hide unfinished improvments 2017-05-23 22:39:33 -04:00
didier amyot dfefef815b fix rebasing 2017-05-23 22:37:04 -04:00
didier amyot e34b213327 blah blah blah 2017-05-23 22:35:11 -04:00
didier amyot f67080571a stuff 2017-05-23 22:33:30 -04:00
didier amyot 5d630e28f4 added new schedule 2017-05-13 09:58:11 -04:00
didier amyot 337508e72a changed parc to fucking george vernot 2017-05-07 10:07:29 -04:00
didier amyot ae5b3365e2 added season 2017 email 2017-05-06 10:44:36 -04:00
didier amyot 5a0582a37b fixed build.js 2017-04-23 11:28:48 -04:00
didier amyot f711a5876d moved away from bower 2017-04-23 11:19:06 -04:00
didier amyot bb3a616f7c saison retarde 2017-04-23 10:21:57 -04:00
didier amyot 3c9cacd8ea changed dated 2017-03-19 09:28:43 -04:00
didier amyot 378e8ab7cc updated message 2017-03-19 08:56:36 -04:00
didier amyot cc73d82288 oupsi 2017-03-18 16:32:57 -04:00
didier amyot 7fc849842f new season inscrition time! 2017-03-18 09:16:04 -04:00
didier amyot 16d8c290d8 updted game schedule 2017-03-16 20:45:09 -04:00
didier amyot 09a08a3c68 changed parc 2017-03-16 20:05:53 -04:00
didier amyot dd932664e0 updated uikit version 2017-02-19 11:09:55 -05:00
didier amyot d08ffff206 updated last meeting updates 2017-02-19 10:51:47 -05:00
didier amyot da77c69063 Update resultats.yaml 2016-09-13 12:41:01 +00:00
didier amyot a0e5a806ef Update resultats.yaml 2016-09-11 22:48:47 +00:00
didier amyot 2576d75f2f Update resultats.yaml 2016-09-06 13:08:20 +00:00
didier amyot 62a18dbd6d Update resultats.yaml 2016-08-31 13:22:05 +00:00
didier amyot dd089045d2 ended final regular season 2016-08-29 19:40:07 -04:00
didier amyot 450cd26ff0 added new scores 2016-08-19 13:55:32 -04:00
didier amyot 7129c334a6 added new games 2016-08-18 13:48:54 -04:00
didier amyot 06eade5a4d Update resultats.yaml 2016-08-17 02:09:23 +00:00
didier amyot 56d893e6a4 Update resultats.yaml 2016-08-15 20:12:21 +00:00
didier amyot 93776f6b72 Update resultats.yaml 2016-08-11 20:18:57 +00:00
didier amyot a89892e2fb Update resultats.yaml 2016-07-22 20:14:49 +00:00
didier amyot f5d343aca2 Update resultats.yaml 2016-07-15 17:57:15 +00:00
didier amyot 6b0652092c ordered the team results 2016-07-12 13:32:10 -04:00
didier amyot b36c7ebcdc Update resultats.yaml 2016-07-08 15:22:55 +00:00
didier amyot 7181d871c0 Update resultats.yaml 2016-07-06 11:53:47 +00:00
didier amyot 9690b60a6d Update resultats.yaml 2016-07-06 02:17:47 +00:00
didier amyot 76950581b4 added new result 2016-06-26 09:30:40 -04:00
didier amyot 813a4968b0 added rain day for today 2016-06-16 17:58:04 -04:00
didier amyot 7a447278be Update resultats.yaml 2016-06-11 15:21:58 +00:00
didier amyot 418e161cc7 fix result typo 2016-06-10 16:42:51 -04:00
didier amyot fe1ed751e1 added cache to gitlab pages 2016-06-10 15:41:46 -04:00
didier amyot df9d8b9109 changed cache buster 2016-06-10 18:30:37 +00:00
didier amyot 41a563ff34 updated results 2016-06-10 18:04:03 +00:00
didier amyot b3e48ebdfa added cache buster in for all result url 2016-06-02 08:48:55 -04:00
didier amyot 137912eaa4 added cache buster 2016-06-02 08:45:22 -04:00
didier amyot a0ae5e89b7 re-added new schedule 2016-06-01 19:15:21 -04:00
didier amyot de0b35f476 cancel season (or almost) 2016-05-11 19:36:05 -04:00
didier amyot 3eae9143fa added real schedule! 2016-05-06 19:47:44 +00:00
didier amyot 61f32a74da fixed many bugs 2016-04-30 11:06:30 -04:00
didier amyot 7e54032605 pined node version in build pack 2016-04-27 20:10:19 -04:00
didier amyot 18938a77d0 changed way to get encrypted data to make cross server requests possible 2016-04-27 19:40:01 -04:00
didier amyot d1c01b6bf9 pointed player list to private repo 2016-04-23 23:53:26 -04:00
didier amyot 1d0a2d4b22 renamed files 2016-04-23 23:34:03 -04:00
didier amyot 930f3cc799 added spritz in build.js 2016-04-23 23:23:55 -04:00
didier amyot 15120d48fc use https instead of ssh for npm 2016-04-23 23:19:22 -04:00
didier amyot bc5a3ce364 added default params to deployemnt 2016-04-23 23:11:04 -04:00
didier amyot 2a689dd20b added encryption to player list 2016-04-23 23:02:19 -04:00
didier amyot 9f113a8588 fixed article order 2016-03-31 09:49:37 -04:00
didier amyot 1d1b697d46 added a new news 2016-03-31 09:01:35 -04:00
didier amyot 9e794ed81e change website url 2016-03-20 00:49:57 +00:00
didier amyot 325360084b improved dropdown nav for cell phones 2016-03-19 17:42:51 -04:00
didier amyot d7ce36f1bc improved top bar for small devices 2016-03-19 15:31:56 -04:00
didier amyot a158a9e323 re-implemented user details 2016-03-19 13:42:20 -04:00
didier amyot efd279691a refactored out the players page 2016-03-19 13:07:05 -04:00
didier amyot bfd839b4cb refactored login page out 2016-03-19 12:59:56 -04:00
didier amyot 73f4f3b8e0 fixed bugs on member page 2016-03-19 12:45:34 -04:00
Comite Ballephenix d6be795177 updated readme files with the new repo url 2016-03-18 01:27:06 +00:00
didier amyot 999bf1afd5 updated public information 2016-03-17 20:00:58 -04:00
97 changed files with 10607 additions and 1989 deletions

No files matched your search

-3
View File
@@ -1,3 +0,0 @@
{
"directory": "lib"
}
+2
View File
@@ -4,3 +4,5 @@ css/*
/api/resultats.json /api/resultats.json
/index.html /index.html
/main-built.js /main-built.js
/api
result
+16 -18
View File
@@ -1,21 +1,19 @@
image: node image: nixos/nix
before_script: workflow:
# install ssh-agent rules:
- 'which npm || ( apt-get update -y && apt-get install node -y )' - if: $CI_COMMIT_BRANCH
pages: pages:
stage: deploy stage: deploy
script: script:
- npm install - mkdir -p "$HOME/.config/nix"
- node_modules/.bin/gulp prod - echo 'experimental-features = nix-command flakes' > "$HOME/.config/nix/nix.conf"
- node_modules/.bin/r.js -o build.js - nix build
- rm -rf node_modules .public public - cp -r result/ public
- mkdir .public artifacts:
- cp -r * .public paths:
- mv .public public - public
artifacts: rules:
paths: - if: $CI_COMMIT_BRANCH == "main"
- public environment: production
only:
- master
+3 -2
View File
@@ -1,11 +1,12 @@
# Site Web de Balle Phénix # Site Web de Balle Phénix
![Image Alt](https://gitlab.com/didiercrunch/phenix-website/raw/master/images/phenix_logo.png) ![Image Alt](https://gitlab.com/ballephenix/website/raw/master/images/phenix_logo.png)
## introduction ## introduction
Vous trouverez le code source du site web pour les Phénix ici. Le site web Vous trouverez le code source du site web pour les Phénix ici. Le site web
en lui-même est accessible au https://didiercrunch.gitlab.io/phenix-website/. en lui-même est accessible au http://ballephenix.com ou au
https://ballephenix.gitlab.io/website/.
### Structure du site web. ### Structure du site web.
-27
View File
@@ -1,27 +0,0 @@
{
"name": "phenix-website",
"description": "Main web site of Balle Phénix.",
"main": "index.html",
"authors": [
"didier amyot <didier.amyot@gmail.com>"
],
"license": "MIT",
"moduleType": [],
"homepage": "",
"private": true,
"ignore": [
"**/.*",
"node_modules",
"bower_components",
"lib",
"test",
"tests"
],
"dependencies": {
"uikit": "~2.24.3",
"mithril": "~0.2.1",
"lodash": "~4.2.1",
"almond": "~0.3.1",
"requirejs": "~2.1.22"
}
}
-11
View File
@@ -1,11 +0,0 @@
({
baseUrl: "script",
paths: {
m: '../lib/mithril/mithril.min',
_: '../lib/lodash/dist/lodash.min',
requireLib: '../lib/requirejs/require'
},
include: 'main',
name: "../lib/almond/almond",
out: "main-built.js"
})
-190
View File
@@ -1,190 +0,0 @@
<!doctype html>
<html>
<head>
<title>Balle Phenix</title>
<link rel="stylesheet" href="css/style.css" />
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/font-awesome/4.5.0/css/font-awesome.min.css">
<script src="lib/mithril/mithril.min.js"></script>
</head>
<body>
<nav class="uk-navbar">
<div class="uk-navbar-content uk-navbar-center">
<ul class="uk-navbar-nav">
<li class="uk-parent">
<a href="https://www.facebook.com/LigueDeBalleLesPhenix">
<i class="fa fa-facebook-square"></i>
</a>
</li>
<li class="uk-parent"><a href="/">Acceuil</a></li>
<li class="uk-active"><a href="">Calendrier</a></li>
<li class="uk-parent"><a>Règlements</a></li>
<li class="uk-parent"><a>Photos</a></li>
<li class="uk-parent"><a>Membre</a></li>
<li class="uk-parent"><a>Nous Joindre</a></li>
</ul>
</div>
</nav>
<div class="uk-grid">
<div class="uk-width-1-5"></div>
<div class="uk-width-3-5">
<div class="uk-grid">
<div class="uk-width-5-5">
<h2>Classement 2015</h2>
<table class="uk-table uk-table-hover uk-table-striped">
<thead>
<tr>
<th>Équipes</th>
<th>PJ</th>
<th>V</th>
<th>D</th>
<th>N</th>
<th>PP</th>
<th>PC</th>
<th>DIF</th>
<th>PTS</th>
</tr>
</thead>
<tbody>
<tr>
<td>Verts</td>
<td>14</td>
<td>11</td>
<td>3</td>
<td>0</td>
<td>161</td>
<td>108</td>
<td>+53</td>
<td>22</td>
</tr>
<tr>
<td>Verts</td>
<td>14</td>
<td>11</td>
<td>3</td>
<td>0</td>
<td>161</td>
<td>108</td>
<td>+53</td>
<td>22</td>
</tr>
<tr>
<td>Verts</td>
<td>14</td>
<td>11</td>
<td>3</td>
<td>0</td>
<td>161</td>
<td>108</td>
<td>+53</td>
<td>22</td>
</tr>
<tr>
<td>Verts</td>
<td>14</td>
<td>11</td>
<td>3</td>
<td>0</td>
<td>161</td>
<td>108</td>
<td>+53</td>
<td>22</td>
</tr>
</tbody>
</table>
<ul class="uk-subnav uk-subnav-line uk-flex-center">
<li>PJ : Parties joués </li><li> V : Victoire </li><li> D : Défaite </li><li> N : Nul </li><li> PP : Points pour </li><li> PC : Points contre </li><li> DIF : Diférenciel </li><li> PTS : Points </li>
</ul>
</div>
</div>
<div class="uk-grid">
<div class="uk-width-3-5">
<h2>Calendrier 2015</h2>
<h3 style="text-align: left;">5 mai 2016</h3>
<table class="uk-table uk-table-hover uk-table-condensed uk-table-striped">
<tr>
<td>18h30</td>
<td><i class="fa fa-flag" style="color: purple;"></i> Mauve</td>
<td>8</td>
<td>vs</td>
<td><i class="fa fa-flag" style="color: red;"></i> Rouge</td>
<td>7</td>
</tr>
<tr>
<td>18h30</td>
<td><i class="fa fa-flag" style="color: yellow;"></i> Jaune</td>
<td>00</td>
<td>vs</td>
<td><i class="fa fa-flag" style="color: gray;"></i> Gris</td>
<td>00</td>
</tr>
</table>
</div>
</div>
</div>
<div class="uk-width-1-5"></div>
</div>
<footer class="uk-grid ph-footer" style="padding: 80px;">
<div class="uk-container uk-container-center uk-text-center">
<div class="uk-panel">
Ligue de balle les Phénix &hellip; pour le plaisir de jouer!
</div>
<ul class="uk-subnav uk-subnav-line uk-flex-center">
<li><a href="mailto:info@ballephenix.com">info@ballephenix.com</a></li>
</ul>
<h1>
<a href="https://www.facebook.com/LigueDeBalleLesPhenix">
<i class="fa fa-facebook-square"></i>
</a>
</h1>
</div>
</footer>
</body>
</html>
-59
View File
@@ -1,59 +0,0 @@
[title]
innerMarkdown = """
## Inscription 2016!
"""
[meta]
innerMarkdown = """
Lundi 14 mars 2016
"""
[body]
innerMarkdown = """
Bonjour à tous les phénixiens phénixiennes.
Eh bien oui l'hiver tire à ça fin et il sera bientôt temps de sortir gants et
batons (en bon français mites et battes) pour jouer à notre sport préféré:
la balle-molle.
**L'inscription aura lieu le vendredi 18 mars 2016 de 19h30 à 21h30 à la [taverne
le normandie](http://bit.ly/1pmNWu8)**; situé au [1295 rue amherst,
Montréal](http://bit.ly/1QUC6Ou). Il s'agit de l'endroit ou nous avons fêté la
fin de la dernière saison.
Le prix de l'inscription est de 110$ incluant la location du chandail au coût de
10$. La valeur de la location du chandail vous sera rendu en fin de saison
lorsque vous le rendrez.
Pour ceux et celles qui ne pourront être présent à l'inscription, vous pouvez
vous inscrire par courrier. Imprimez, remplissez et envoyez le formulaire
avec le chèque.
Nous avons très hâte de vous y voir et de fêter avec vous!!!
Votre comité de balle les phénix.
"""
[smallBody]
innerMarkdown = """
Bonjour à tous les phénixiens phénixiennes.
Eh bien oui l'hiver tire à ça fin et il sera bientôt temps de sortir gants et
batons (en bon français mites et battes) pour jouer à notre sport préféré:
la balle-molle.
**L'inscription aura lieu le vendredi 18 mars 2016 de 19h30 à 21h30 à la [taverne
le normandie](http://bit.ly/1pmNWu8)**; situé au [1295 rue amherst,
Montréal](http://bit.ly/1QUC6Ou). Il s'agit de l'endroit ou nous avons fêté la
fin de la dernière saison.
**[lire la suite ...](#/nouvelles)**
"""
-289
View File
@@ -1,289 +0,0 @@
---
-
email: fleet80@hickle.org
name: "Delle Emmerich"
score: 2
team: rouge
tel: 613-805-2793x858
-
email: qschamberger@yahoo.com
name: "Susie Quitzon MD"
score: 3
team: rouge
tel: 1-332-714-0777x97469
-
email: kianna90@yahoo.com
name: "Johnathan Leuschke"
score: 5
team: jaune
tel: 974-275-2040
-
email: susannah.grant@hotmail.com
name: "Dr. Wendell Sporer"
score: 3
team: rouge
tel: 04691879363
-
email: millicent46@adams.info
name: "Emile Powlowski II"
score: 1
team: bleu
tel: 1-449-950-7363x2633
-
email: cormier.codi@hotmail.com
name: "Gardner Willms"
score: 2
team: bleu
tel: 625-516-1325
-
email: kamryn.kovacek@gmail.com
name: "Aliya Vandervort"
score: 4
team: rouge
tel: "250.915.3706"
-
email: marian97@beahan.org
name: "Gaige Kautzer"
score: 2
team: gris
tel: "298.694.0319"
-
email: patsy.kerluke@satterfieldberge.com
name: "Orilla Brakus"
score: 5
team: rouge
tel: (506)015-3098x8355
-
email: alpha30@connelly.com
name: "Dr. Thurman O'Hara"
score: 5
team: bleu
tel: 07469452414
-
email: thompson.willene@gmail.com
name: "Rachael Medhurst DDS"
score: 2
team: rouge
tel: 1-602-031-0376
-
email: inader@kunze.info
name: "Mr. Ingram Thompson"
score: 2
team: rouge
tel: (109)873-9483x211
-
email: desiree.harris@gmail.com
name: "Dr. Saul Streich Jr."
score: 5
team: gris
tel: 1-249-486-6759x84328
-
email: samir83@hills.com
name: "Kimberley Kihn"
score: 5
team: jaune
tel: 304.586.6687x3262
-
email: egrady@emmerichpadberg.com
name: "Arra Boyer"
score: 3
team: gris
tel: "485.730.8331"
-
email: bgoodwin@gmail.com
name: "Miss Kaylan Robel DVM"
score: 4
team: gris
tel: "321.945.7155"
-
email: angelic86@homenick.com
name: "Kyson Ruecker"
score: 4
team: bleu
tel: 1-017-690-5278
-
email: val.sawayn@gmail.com
name: "Shaun Goodwin"
score: 3
team: jaune
tel: (271)085-2639x251
-
email: kya.wunsch@gmail.com
name: "Mr. Denzell Casper"
score: 2
team: bleu
tel: 948-754-1786x17035
-
email: delmus18@stoltenberg.org
name: "Bluford Marvin Jr."
score: 2
team: jaune
tel: (268)984-3065x3634
-
email: kihn.zackery@gmail.com
name: "Lucio Kub"
score: 2
team: jaune
tel: 185-942-2355x8756
-
email: jade24@aufderharkuhic.com
name: "Mr. Justice Pollich DVM"
score: 1
team: bleu
tel: 1-918-319-1713
-
email: vgoyette@hotmail.com
name: "Bose Ankunding"
score: 4
team: gris
tel: "265.582.6145"
-
email: raltenwerth@lueilwitz.com
name: "Harlen Harber"
score: 1
team: jaune
tel: (081)424-2803
-
email: thiel.bode@reynolds.info
name: "Linnie Abshire"
score: 1
team: rouge
tel: 1-809-325-8148x5271
-
email: istracke@lueilwitz.com
name: "Mr. Juwan Zemlak"
score: 5
team: jaune
tel: 982.535.6849x5299
-
email: boysie44@hartmanngraham.com
name: "Mr. Tahj Bernhard"
score: 1
team: rouge
tel: +57(9)5038029147
-
email: harm91@dare.net
name: "Dr. Lyle Lakin PhD"
score: 4
team: bleu
tel: 079-078-9724
-
email: prosacco.dolphus@dickens.com
name: "Bertram Schuster"
score: 4
team: gris
tel: (917)409-8168x00826
-
email: elian04@stroman.com
name: "Viviana Howell"
score: 5
team: rouge
tel: 1-414-103-3954x02444
-
email: hakim08@hotmail.com
name: "Marques Goodwin"
score: 1
team: rouge
tel: (649)195-3556x81548
-
email: nigel.kilback@gmail.com
name: "Rayfield Lubowitz"
score: 2
team: bleu
tel: (231)457-7181
-
email: rogahn.tollie@lehnerwillms.com
name: "Miss Luz Altenwerth"
score: 3
team: gris
tel: 00248382520
-
email: reilly.velia@hansenhegmann.com
name: "Lilly Brekke"
score: 1
team: rouge
tel: 006.284.1261x54374
-
email: batz.dessa@rippin.org
name: "Jay Aufderhar"
score: 3
team: rouge
tel: 960-144-7624x406
-
email: garth.barton@kerluke.com
name: "Ms. Contina Pfeffer DDS"
score: 5
team: jaune
tel: (352)043-9218x9064
-
email: mmcglynn@gusikowski.com
name: "Robyn Lakin"
score: 1
team: bleu
tel: 667-492-9674x3911
-
email: breinger@yahoo.com
name: "Latonia Kuhlman"
score: 2
team: bleu
tel: 404.860.5529x107
-
email: jamarion.sipes@gmail.com
name: "Dr. Camryn Goyette"
score: 4
team: bleu
tel: 648-481-0991x380
-
email: consuelo37@gmail.com
name: "Khloe Altenwerth"
score: 4
team: gris
tel: 1-480-994-8256x873
-
email: icie.kohler@murphyrohan.com
name: "Pearl Dicki"
score: 1
team: rouge
tel: +04(3)0376370559
-
email: miya43@yahoo.com
name: "Christoper Botsford"
score: 2
team: gris
tel: (731)031-5128x77337
-
email: xschmidt@yahoo.com
name: "Lauren Bins"
score: 1
team: gris
tel: (503)215-2332x77244
-
email: rempel.earley@waelchi.net
name: "Sigmund Stroman"
score: 4
team: rouge
tel: (719)103-8927x0887
-
email: gustav.graham@kihn.com
name: "Brook Nolan"
score: 2
team: gris
tel: "642.931.3403"
-
email: hettinger.emit@cartwright.com
name: "Mr. Gaston Bartell"
score: 5
team: jaune
tel: "00536147705"
-
email: tlittle@marquardtfunk.info
name: "Ansel Schimmel"
score: 3
team: bleu
tel: (432)161-1237
-
email: blangosh@hotmail.com
name: "Kiefer Funk"
score: 3
team: rouge
tel: 224-921-0391x3813
-17
View File
@@ -1,17 +0,0 @@
---
-
date: ~
time: ~
home: gris
away: jaune
home_points: ~
away_points: !
-
date: ~
time: ~
home: bleu
away: rouge
home_points: ~
away_points: ~
+10
View File
@@ -0,0 +1,10 @@
{
"deploy": {
"project": "7a93d03e-eabe-4db1-b78e-5f1bbcb460b0",
"exclude": [
"**/node_modules"
],
"include": [],
"entrypoint": "server.ts"
}
}
Generated
+280
View File
@@ -0,0 +1,280 @@
{
"version": "3",
"packages": {
"specifiers": {
"jsr:@oak/commons@0.11": "jsr:@oak/commons@0.11.0",
"jsr:@oak/oak": "jsr:@oak/oak@16.1.0",
"jsr:@std/assert@0.223": "jsr:@std/assert@0.223.0",
"jsr:@std/assert@0.226": "jsr:@std/assert@0.226.0",
"jsr:@std/assert@^0.223.0": "jsr:@std/assert@0.223.0",
"jsr:@std/assert@^0.224.0": "jsr:@std/assert@0.224.0",
"jsr:@std/bytes@0.223": "jsr:@std/bytes@0.223.0",
"jsr:@std/bytes@0.224": "jsr:@std/bytes@0.224.0",
"jsr:@std/bytes@^0.223.0": "jsr:@std/bytes@0.223.0",
"jsr:@std/crypto@0.223": "jsr:@std/crypto@0.223.0",
"jsr:@std/crypto@0.224": "jsr:@std/crypto@0.224.0",
"jsr:@std/encoding@1.0.0-rc.2": "jsr:@std/encoding@1.0.0-rc.2",
"jsr:@std/encoding@^0.223.0": "jsr:@std/encoding@0.223.0",
"jsr:@std/http@0.223": "jsr:@std/http@0.223.0",
"jsr:@std/http@0.224": "jsr:@std/http@0.224.5",
"jsr:@std/io@0.223": "jsr:@std/io@0.223.0",
"jsr:@std/media-types@0.223": "jsr:@std/media-types@0.223.0",
"jsr:@std/media-types@0.224": "jsr:@std/media-types@0.224.1",
"jsr:@std/path@0.223": "jsr:@std/path@0.223.0",
"npm:path-to-regexp@6.2.1": "npm:path-to-regexp@6.2.1"
},
"jsr": {
"@oak/commons@0.11.0": {
"integrity": "07702bfe5c07cd8144c422022994da1f9fea466b185824f4be63a2b1b1a65125",
"dependencies": [
"jsr:@std/assert@0.226",
"jsr:@std/bytes@0.224",
"jsr:@std/crypto@0.224",
"jsr:@std/http@0.224",
"jsr:@std/media-types@0.224"
]
},
"@oak/oak@16.1.0": {
"integrity": "ab21506555fffeb08dc8f45ff5d28607e8087949ff58bd2964b27df65994480b",
"dependencies": [
"jsr:@oak/commons@0.11",
"jsr:@std/assert@0.223",
"jsr:@std/bytes@0.223",
"jsr:@std/crypto@0.223",
"jsr:@std/http@0.223",
"jsr:@std/io@0.223",
"jsr:@std/media-types@0.223",
"jsr:@std/path@0.223",
"npm:path-to-regexp@6.2.1"
]
},
"@std/assert@0.223.0": {
"integrity": "eb8d6d879d76e1cc431205bd346ed4d88dc051c6366365b1af47034b0670be24"
},
"@std/assert@0.224.0": {
"integrity": "8643233ec7aec38a940a8264a6e3eed9bfa44e7a71cc6b3c8874213ff401967f"
},
"@std/assert@0.226.0": {
"integrity": "0dfb5f7c7723c18cec118e080fec76ce15b4c31154b15ad2bd74822603ef75b3"
},
"@std/bytes@0.223.0": {
"integrity": "84b75052cd8680942c397c2631318772b295019098f40aac5c36cead4cba51a8"
},
"@std/bytes@0.224.0": {
"integrity": "a2250e1d0eb7d1c5a426f21267ab9bdeac2447fa87a3d0d1a467d3f7a6058e49"
},
"@std/crypto@0.223.0": {
"integrity": "1aa9555ff56b09e197ad988ea200f84bc6781fd4fd83f3a156ee44449af93000",
"dependencies": [
"jsr:@std/assert@^0.223.0",
"jsr:@std/encoding@^0.223.0"
]
},
"@std/crypto@0.224.0": {
"integrity": "154ef3ff08ef535562ef1a718718c5b2c5fc3808f0f9100daad69e829bfcdf2d",
"dependencies": [
"jsr:@std/assert@^0.224.0"
]
},
"@std/encoding@0.223.0": {
"integrity": "2b5615a75e00337ce113f34cf2f9b8c18182c751a8dcc8b1a2c2fc0e117bef00"
},
"@std/encoding@1.0.0-rc.2": {
"integrity": "160d7674a20ebfbccdf610b3801fee91cf6e42d1c106dd46bbaf46e395cd35ef"
},
"@std/http@0.223.0": {
"integrity": "15ab8a0c5a7e9d5be017a15b01600f20f66602ceec48b378939fa24fcec522aa",
"dependencies": [
"jsr:@std/assert@^0.223.0",
"jsr:@std/encoding@^0.223.0"
]
},
"@std/http@0.224.5": {
"integrity": "b03b5d1529f6c423badfb82f6640f9f2557b4034cd7c30655ba5bb447ff750a4",
"dependencies": [
"jsr:@std/encoding@1.0.0-rc.2"
]
},
"@std/io@0.223.0": {
"integrity": "2d8c3c2ab3a515619b90da2c6ff5ea7b75a94383259ef4d02116b228393f84f1",
"dependencies": [
"jsr:@std/bytes@^0.223.0"
]
},
"@std/media-types@0.223.0": {
"integrity": "84684680c2eb6bc6d9369c6d6f26a49decaf2c7603ff531862dda575d9d6776e"
},
"@std/media-types@0.224.1": {
"integrity": "9e69a5daed37c5b5c6d3ce4731dc191f80e67f79bed392b0957d1d03b87f11e1"
},
"@std/path@0.223.0": {
"integrity": "593963402d7e6597f5a6e620931661053572c982fc014000459edc1f93cc3989",
"dependencies": [
"jsr:@std/assert@^0.223.0"
]
}
},
"npm": {
"path-to-regexp@6.2.1": {
"integrity": "sha512-JLyh7xT1kizaEvcaXOQwOc2/Yhw6KZOvPf1S8401UyLk86CU79LN3vl7ztXGm/pZ+YjoyAJ4rxmHwbkBXJX+yw==",
"dependencies": {}
}
}
},
"remote": {
"https://deno.land/std@0.205.0/assert/assert.ts": "9a97dad6d98c238938e7540736b826440ad8c1c1e54430ca4c4e623e585607ee",
"https://deno.land/std@0.205.0/assert/assertion_error.ts": "4d0bde9b374dfbcbe8ac23f54f567b77024fb67dbb1906a852d67fe050d42f56",
"https://deno.land/std@0.205.0/html/entities.ts": "43f208131bb847e6e222c9dd50322066491da93ed945a93d778923ef7e975398",
"https://deno.land/std@0.205.0/html/mod.ts": "3f8c71781e32037ab63bd417759d15d31fb9606c6615c85dcabcc515986494ba",
"https://deno.land/std@0.205.0/path/_common/assert_path.ts": "061e4d093d4ba5aebceb2c4da3318bfe3289e868570e9d3a8e327d91c2958946",
"https://deno.land/std@0.205.0/path/_common/basename.ts": "0d978ff818f339cd3b1d09dc914881f4d15617432ae519c1b8fdc09ff8d3789a",
"https://deno.land/std@0.205.0/path/_common/common.ts": "9e4233b2eeb50f8b2ae10ecc2108f58583aea6fd3e8907827020282dc2b76143",
"https://deno.land/std@0.205.0/path/_common/constants.ts": "e49961f6f4f48039c0dfed3c3f93e963ca3d92791c9d478ac5b43183413136e0",
"https://deno.land/std@0.205.0/path/_common/dirname.ts": "2ba7fb4cc9fafb0f38028f434179579ce61d4d9e51296fad22b701c3d3cd7397",
"https://deno.land/std@0.205.0/path/_common/format.ts": "11aa62e316dfbf22c126917f5e03ea5fe2ee707386555a8f513d27ad5756cf96",
"https://deno.land/std@0.205.0/path/_common/from_file_url.ts": "ef1bf3197d2efbf0297a2bdbf3a61d804b18f2bcce45548ae112313ec5be3c22",
"https://deno.land/std@0.205.0/path/_common/glob_to_reg_exp.ts": "5c3c2b79fc2294ec803d102bd9855c451c150021f452046312819fbb6d4dc156",
"https://deno.land/std@0.205.0/path/_common/is_glob.ts": "567dce5c6656bdedfc6b3ee6c0833e1e4db2b8dff6e62148e94a917f289c06ad",
"https://deno.land/std@0.205.0/path/_common/normalize.ts": "2ba7fb4cc9fafb0f38028f434179579ce61d4d9e51296fad22b701c3d3cd7397",
"https://deno.land/std@0.205.0/path/_common/normalize_string.ts": "88c472f28ae49525f9fe82de8c8816d93442d46a30d6bb5063b07ff8a89ff589",
"https://deno.land/std@0.205.0/path/_common/relative.ts": "1af19d787a2a84b8c534cc487424fe101f614982ae4851382c978ab2216186b4",
"https://deno.land/std@0.205.0/path/_common/strip_trailing_separators.ts": "7ffc7c287e97bdeeee31b155828686967f222cd73f9e5780bfe7dfb1b58c6c65",
"https://deno.land/std@0.205.0/path/_common/to_file_url.ts": "a8cdd1633bc9175b7eebd3613266d7c0b6ae0fb0cff24120b6092ac31662f9ae",
"https://deno.land/std@0.205.0/path/_interface.ts": "6471159dfbbc357e03882c2266d21ef9afdb1e4aa771b0545e90db58a0ba314b",
"https://deno.land/std@0.205.0/path/_os.ts": "30b0c2875f360c9296dbe6b7f2d528f0f9c741cecad2e97f803f5219e91b40a2",
"https://deno.land/std@0.205.0/path/basename.ts": "04bb5ef3e86bba8a35603b8f3b69537112cdd19ce64b77f2522006da2977a5f3",
"https://deno.land/std@0.205.0/path/common.ts": "f4d061c7d0b95a65c2a1a52439edec393e906b40f1caf4604c389fae7caa80f5",
"https://deno.land/std@0.205.0/path/dirname.ts": "88a0a71c21debafc4da7a4cd44fd32e899462df458fbca152390887d41c40361",
"https://deno.land/std@0.205.0/path/extname.ts": "2da4e2490f3b48b7121d19fb4c91681a5e11bd6bd99df4f6f47d7a71bb6ecdf2",
"https://deno.land/std@0.205.0/path/format.ts": "3457530cc85d1b4bab175f9ae73998b34fd456c830d01883169af0681b8894fb",
"https://deno.land/std@0.205.0/path/from_file_url.ts": "e7fa233ea1dff9641e8d566153a24d95010110185a6f418dd2e32320926043f8",
"https://deno.land/std@0.205.0/path/glob.ts": "9c77cf47db1d786e2ebf66670824d03fd84ecc7c807cac24441eb9d5cb6a2986",
"https://deno.land/std@0.205.0/path/is_absolute.ts": "67232b41b860571c5b7537f4954c88d86ae2ba45e883ee37d3dec27b74909d13",
"https://deno.land/std@0.205.0/path/join.ts": "98d3d76c819af4a11a81d5ba2dbb319f1ce9d63fc2b615597d4bcfddd4a89a09",
"https://deno.land/std@0.205.0/path/mod.ts": "2d62a0a8b78a60e8e6f485d881bac6b61d58573b11cf585fb7c8fc50d9b20d80",
"https://deno.land/std@0.205.0/path/normalize.ts": "aa95be9a92c7bd4f9dc0ba51e942a1973e2b93d266cd74f5ca751c136d520b66",
"https://deno.land/std@0.205.0/path/parse.ts": "d87ff0deef3fb495bc0d862278ff96da5a06acf0625ca27769fc52ac0d3d6ece",
"https://deno.land/std@0.205.0/path/posix/_util.ts": "ecf49560fedd7dd376c6156cc5565cad97c1abe9824f4417adebc7acc36c93e5",
"https://deno.land/std@0.205.0/path/posix/basename.ts": "a630aeb8fd8e27356b1823b9dedd505e30085015407caa3396332752f6b8406a",
"https://deno.land/std@0.205.0/path/posix/common.ts": "e781d395dc76f6282e3f7dd8de13194abb8b04a82d109593141abc6e95755c8b",
"https://deno.land/std@0.205.0/path/posix/dirname.ts": "f48c9c42cc670803b505478b7ef162c7cfa9d8e751b59d278b2ec59470531472",
"https://deno.land/std@0.205.0/path/posix/extname.ts": "ee7f6571a9c0a37f9218fbf510c440d1685a7c13082c348d701396cc795e0be0",
"https://deno.land/std@0.205.0/path/posix/format.ts": "b94876f77e61bfe1f147d5ccb46a920636cd3cef8be43df330f0052b03875968",
"https://deno.land/std@0.205.0/path/posix/from_file_url.ts": "b97287a83e6407ac27bdf3ab621db3fccbf1c27df0a1b1f20e1e1b5acf38a379",
"https://deno.land/std@0.205.0/path/posix/glob.ts": "86c3f06d1c98303613c74650961c3e24bdb871cde2a97c3ae7f0f6d4abbef445",
"https://deno.land/std@0.205.0/path/posix/is_absolute.ts": "159900a3422d11069d48395568217eb7fc105ceda2683d03d9b7c0f0769e01b8",
"https://deno.land/std@0.205.0/path/posix/join.ts": "0c0d84bdc344876930126640011ec1b888e6facf74153ffad9ef26813aa2a076",
"https://deno.land/std@0.205.0/path/posix/mod.ts": "6bfa8a42d85345b12dbe8571028ca2c62d460b6ef968125e498602b43b6cf6b6",
"https://deno.land/std@0.205.0/path/posix/normalize.ts": "11de90a94ab7148cc46e5a288f7d732aade1d616bc8c862f5560fa18ff987b4b",
"https://deno.land/std@0.205.0/path/posix/parse.ts": "199208f373dd93a792e9c585352bfc73a6293411bed6da6d3bc4f4ef90b04c8e",
"https://deno.land/std@0.205.0/path/posix/relative.ts": "e2f230608b0f083e6deaa06e063943e5accb3320c28aef8d87528fbb7fe6504c",
"https://deno.land/std@0.205.0/path/posix/resolve.ts": "51579d83159d5c719518c9ae50812a63959bbcb7561d79acbdb2c3682236e285",
"https://deno.land/std@0.205.0/path/posix/separator.ts": "0b6573b5f3269a3164d8edc9cefc33a02dd51003731c561008c8bb60220ebac1",
"https://deno.land/std@0.205.0/path/posix/to_file_url.ts": "08d43ea839ee75e9b8b1538376cfe95911070a655cd312bc9a00f88ef14967b6",
"https://deno.land/std@0.205.0/path/posix/to_namespaced_path.ts": "c9228a0e74fd37e76622cd7b142b8416663a9b87db643302fa0926b5a5c83bdc",
"https://deno.land/std@0.205.0/path/relative.ts": "23d45ede8b7ac464a8299663a43488aad6b561414e7cbbe4790775590db6349c",
"https://deno.land/std@0.205.0/path/resolve.ts": "5b184efc87155a0af9fa305ff68a109e28de9aee81fc3e77cd01380f19daf867",
"https://deno.land/std@0.205.0/path/separator.ts": "40a3e9a4ad10bef23bc2cd6c610291b6c502a06237c2c4cd034a15ca78dedc1f",
"https://deno.land/std@0.205.0/path/to_file_url.ts": "edaafa089e0bce386e1b2d47afe7c72e379ff93b28a5829a5885e4b6c626d864",
"https://deno.land/std@0.205.0/path/to_namespaced_path.ts": "cf8734848aac3c7527d1689d2adf82132b1618eff3cc523a775068847416b22a",
"https://deno.land/std@0.205.0/path/windows/_util.ts": "f32b9444554c8863b9b4814025c700492a2b57ff2369d015360970a1b1099d54",
"https://deno.land/std@0.205.0/path/windows/basename.ts": "8a9dbf7353d50afbc5b221af36c02a72c2d1b2b5b9f7c65bf6a5a2a0baf88ad3",
"https://deno.land/std@0.205.0/path/windows/common.ts": "e781d395dc76f6282e3f7dd8de13194abb8b04a82d109593141abc6e95755c8b",
"https://deno.land/std@0.205.0/path/windows/dirname.ts": "5c2aa541384bf0bd9aca821275d2a8690e8238fa846198ef5c7515ce31a01a94",
"https://deno.land/std@0.205.0/path/windows/extname.ts": "07f4fa1b40d06a827446b3e3bcc8d619c5546b079b8ed0c77040bbef716c7614",
"https://deno.land/std@0.205.0/path/windows/format.ts": "343019130d78f172a5c49fdc7e64686a7faf41553268961e7b6c92a6d6548edf",
"https://deno.land/std@0.205.0/path/windows/from_file_url.ts": "d53335c12b0725893d768be3ac6bf0112cc5b639d2deb0171b35988493b46199",
"https://deno.land/std@0.205.0/path/windows/glob.ts": "0286fb89ecd21db5cbf3b6c79e2b87c889b03f1311e66fb769e6b905d4142332",
"https://deno.land/std@0.205.0/path/windows/is_absolute.ts": "245b56b5f355ede8664bd7f080c910a97e2169972d23075554ae14d73722c53c",
"https://deno.land/std@0.205.0/path/windows/join.ts": "e6600bf88edeeef4e2276e155b8de1d5dec0435fd526ba2dc4d37986b2882f16",
"https://deno.land/std@0.205.0/path/windows/mod.ts": "c3d1a36fbf9f6db1320bcb4fbda8de011d25461be3497105e15cbea1e3726198",
"https://deno.land/std@0.205.0/path/windows/normalize.ts": "9deebbf40c81ef540b7b945d4ccd7a6a2c5a5992f791e6d3377043031e164e69",
"https://deno.land/std@0.205.0/path/windows/parse.ts": "120faf778fe1f22056f33ded069b68e12447668fcfa19540c0129561428d3ae5",
"https://deno.land/std@0.205.0/path/windows/relative.ts": "026855cd2c36c8f28f1df3c6fbd8f2449a2aa21f48797a74700c5d872b86d649",
"https://deno.land/std@0.205.0/path/windows/resolve.ts": "5ff441ab18a2346abadf778121128ee71bda4d0898513d4639a6ca04edca366b",
"https://deno.land/std@0.205.0/path/windows/separator.ts": "ae21f27015f10510ed1ac4a0ba9c4c9c967cbdd9d9e776a3e4967553c397bd5d",
"https://deno.land/std@0.205.0/path/windows/to_file_url.ts": "8e9ea9e1ff364aa06fa72999204229952d0a279dbb876b7b838b2b2fea55cce3",
"https://deno.land/std@0.205.0/path/windows/to_namespaced_path.ts": "e0f4d4a5e77f28a5708c1a33ff24360f35637ba6d8f103d19661255ef7bfd50d",
"https://deno.land/std@0.224.0/assert/_constants.ts": "a271e8ef5a573f1df8e822a6eb9d09df064ad66a4390f21b3e31f820a38e0975",
"https://deno.land/std@0.224.0/assert/assert.ts": "09d30564c09de846855b7b071e62b5974b001bb72a4b797958fe0660e7849834",
"https://deno.land/std@0.224.0/assert/assert_almost_equals.ts": "9e416114322012c9a21fa68e187637ce2d7df25bcbdbfd957cd639e65d3cf293",
"https://deno.land/std@0.224.0/assert/assert_array_includes.ts": "14c5094471bc8e4a7895fc6aa5a184300d8a1879606574cb1cd715ef36a4a3c7",
"https://deno.land/std@0.224.0/assert/assert_equals.ts": "3bbca947d85b9d374a108687b1a8ba3785a7850436b5a8930d81f34a32cb8c74",
"https://deno.land/std@0.224.0/assert/assert_exists.ts": "43420cf7f956748ae6ed1230646567b3593cb7a36c5a5327269279c870c5ddfd",
"https://deno.land/std@0.224.0/assert/assert_false.ts": "3e9be8e33275db00d952e9acb0cd29481a44fa0a4af6d37239ff58d79e8edeff",
"https://deno.land/std@0.224.0/assert/assert_greater.ts": "5e57b201fd51b64ced36c828e3dfd773412c1a6120c1a5a99066c9b261974e46",
"https://deno.land/std@0.224.0/assert/assert_greater_or_equal.ts": "9870030f997a08361b6f63400273c2fb1856f5db86c0c3852aab2a002e425c5b",
"https://deno.land/std@0.224.0/assert/assert_instance_of.ts": "e22343c1fdcacfaea8f37784ad782683ec1cf599ae9b1b618954e9c22f376f2c",
"https://deno.land/std@0.224.0/assert/assert_is_error.ts": "f856b3bc978a7aa6a601f3fec6603491ab6255118afa6baa84b04426dd3cc491",
"https://deno.land/std@0.224.0/assert/assert_less.ts": "60b61e13a1982865a72726a5fa86c24fad7eb27c3c08b13883fb68882b307f68",
"https://deno.land/std@0.224.0/assert/assert_less_or_equal.ts": "d2c84e17faba4afe085e6c9123a63395accf4f9e00150db899c46e67420e0ec3",
"https://deno.land/std@0.224.0/assert/assert_match.ts": "ace1710dd3b2811c391946954234b5da910c5665aed817943d086d4d4871a8b7",
"https://deno.land/std@0.224.0/assert/assert_not_equals.ts": "78d45dd46133d76ce624b2c6c09392f6110f0df9b73f911d20208a68dee2ef29",
"https://deno.land/std@0.224.0/assert/assert_not_instance_of.ts": "3434a669b4d20cdcc5359779301a0588f941ffdc2ad68803c31eabdb4890cf7a",
"https://deno.land/std@0.224.0/assert/assert_not_match.ts": "df30417240aa2d35b1ea44df7e541991348a063d9ee823430e0b58079a72242a",
"https://deno.land/std@0.224.0/assert/assert_not_strict_equals.ts": "37f73880bd672709373d6dc2c5f148691119bed161f3020fff3548a0496f71b8",
"https://deno.land/std@0.224.0/assert/assert_object_match.ts": "411450fd194fdaabc0089ae68f916b545a49d7b7e6d0026e84a54c9e7eed2693",
"https://deno.land/std@0.224.0/assert/assert_rejects.ts": "4bee1d6d565a5b623146a14668da8f9eb1f026a4f338bbf92b37e43e0aa53c31",
"https://deno.land/std@0.224.0/assert/assert_strict_equals.ts": "b4f45f0fd2e54d9029171876bd0b42dd9ed0efd8f853ab92a3f50127acfa54f5",
"https://deno.land/std@0.224.0/assert/assert_string_includes.ts": "496b9ecad84deab72c8718735373feb6cdaa071eb91a98206f6f3cb4285e71b8",
"https://deno.land/std@0.224.0/assert/assert_throws.ts": "c6508b2879d465898dab2798009299867e67c570d7d34c90a2d235e4553906eb",
"https://deno.land/std@0.224.0/assert/assertion_error.ts": "ba8752bd27ebc51f723702fac2f54d3e94447598f54264a6653d6413738a8917",
"https://deno.land/std@0.224.0/assert/equal.ts": "bddf07bb5fc718e10bb72d5dc2c36c1ce5a8bdd3b647069b6319e07af181ac47",
"https://deno.land/std@0.224.0/assert/fail.ts": "0eba674ffb47dff083f02ced76d5130460bff1a9a68c6514ebe0cdea4abadb68",
"https://deno.land/std@0.224.0/assert/mod.ts": "48b8cb8a619ea0b7958ad7ee9376500fe902284bb36f0e32c598c3dc34cbd6f3",
"https://deno.land/std@0.224.0/assert/unimplemented.ts": "8c55a5793e9147b4f1ef68cd66496b7d5ba7a9e7ca30c6da070c1a58da723d73",
"https://deno.land/std@0.224.0/assert/unreachable.ts": "5ae3dbf63ef988615b93eb08d395dda771c96546565f9e521ed86f6510c29e19",
"https://deno.land/std@0.224.0/fmt/colors.ts": "508563c0659dd7198ba4bbf87e97f654af3c34eb56ba790260f252ad8012e1c5",
"https://deno.land/std@0.224.0/internal/diff.ts": "6234a4b493ebe65dc67a18a0eb97ef683626a1166a1906232ce186ae9f65f4e6",
"https://deno.land/std@0.224.0/internal/format.ts": "0a98ee226fd3d43450245b1844b47003419d34d210fa989900861c79820d21c2",
"https://deno.land/std@0.224.0/internal/mod.ts": "534125398c8e7426183e12dc255bb635d94e06d0f93c60a297723abe69d3b22e",
"https://deno.land/std@0.84.0/_util/assert.ts": "2f868145a042a11d5ad0a3c748dcf580add8a0dbc0e876eaa0026303a5488f58",
"https://deno.land/std@0.84.0/_util/os.ts": "e282950a0eaa96760c0cf11e7463e66babd15ec9157d4c9ed49cc0925686f6a7",
"https://deno.land/std@0.84.0/path/_constants.ts": "1247fee4a79b70c89f23499691ef169b41b6ccf01887a0abd131009c5581b853",
"https://deno.land/std@0.84.0/path/_interface.ts": "1fa73b02aaa24867e481a48492b44f2598cd9dfa513c7b34001437007d3642e4",
"https://deno.land/std@0.84.0/path/_util.ts": "f4fa69aa3cbbd8568763bfc43c7236875015ba343602d8bafd332b4b4243681b",
"https://deno.land/std@0.84.0/path/common.ts": "eaf03d08b569e8a87e674e4e265e099f237472b6fd135b3cbeae5827035ea14a",
"https://deno.land/std@0.84.0/path/glob.ts": "4a524c1c9da3e79a9fdabdc6e850cd9e41bdf31e442856ffa19c5b123268ca95",
"https://deno.land/std@0.84.0/path/mod.ts": "4465dc494f271b02569edbb4a18d727063b5dbd6ed84283ff906260970a15d12",
"https://deno.land/std@0.84.0/path/posix.ts": "1408f8ba482a4dc5fc0a7cd7be28bbbff9608d2b3b5ffdcf288ae1228d959add",
"https://deno.land/std@0.84.0/path/separator.ts": "8fdcf289b1b76fd726a508f57d3370ca029ae6976fcde5044007f062e643ff1c",
"https://deno.land/std@0.84.0/path/win32.ts": "6ca052f54500f00cd7a5172fde62900626ab620dcd5bdcf4e6f5695d001ddef6",
"https://deno.land/std@0.99.0/_util/assert.ts": "2f868145a042a11d5ad0a3c748dcf580add8a0dbc0e876eaa0026303a5488f58",
"https://deno.land/std@0.99.0/_util/os.ts": "e282950a0eaa96760c0cf11e7463e66babd15ec9157d4c9ed49cc0925686f6a7",
"https://deno.land/std@0.99.0/path/_constants.ts": "1247fee4a79b70c89f23499691ef169b41b6ccf01887a0abd131009c5581b853",
"https://deno.land/std@0.99.0/path/_interface.ts": "1fa73b02aaa24867e481a48492b44f2598cd9dfa513c7b34001437007d3642e4",
"https://deno.land/std@0.99.0/path/_util.ts": "2e06a3b9e79beaf62687196bd4b60a4c391d862cfa007a20fc3a39f778ba073b",
"https://deno.land/std@0.99.0/path/common.ts": "eaf03d08b569e8a87e674e4e265e099f237472b6fd135b3cbeae5827035ea14a",
"https://deno.land/std@0.99.0/path/glob.ts": "314ad9ff263b895795208cdd4d5e35a44618ca3c6dd155e226fb15d065008652",
"https://deno.land/std@0.99.0/path/mod.ts": "4465dc494f271b02569edbb4a18d727063b5dbd6ed84283ff906260970a15d12",
"https://deno.land/std@0.99.0/path/posix.ts": "f56c3c99feb47f30a40ce9d252ef6f00296fa7c0fcb6dd81211bdb3b8b99ca3b",
"https://deno.land/std@0.99.0/path/separator.ts": "8fdcf289b1b76fd726a508f57d3370ca029ae6976fcde5044007f062e643ff1c",
"https://deno.land/std@0.99.0/path/win32.ts": "77f7b3604e0de40f3a7c698e8a79e7f601dc187035a1c21cb1e596666ce112f8",
"https://deno.land/x/media_types@v2.7.1/db.ts": "1d95aa3fc1fe076638550640609394f0e157b18b430800e419aa7ece5c151d9c",
"https://deno.land/x/media_types@v2.7.1/deps.ts": "cd4c31e4b5ed8c4d8c61bd2fb38a82d68d3fd2dcf6d43f22511cbe6d9d310e51",
"https://deno.land/x/media_types@v2.7.1/mod.ts": "d63583b978d32eff8b76e1ae5d83cba2fb27baa90cc1bcb0ad15a06122ea8c19",
"https://deno.land/x/static_files@1.1.6/mod.ts": "8a9bb05599e53864c54eb22931fe98507818517e0d69f26e099a1d8f4ef2b638",
"https://deno.land/x/static_files@1.1.6/src/deps.ts": "fb62be7a780339157bf692a619d6d02ea9662490deca275f488f9f9db917fc4a",
"https://deno.land/x/static_files@1.1.6/src/types.ts": "ef201288626294e9e1b8ee85cdfe2cdfb282e4d78af445df1726050dfa0c0988",
"https://deno.land/x/static_files@1.1.6/src/utils.ts": "9e6172dc97fed01e70a6b063c5afff40e20fe726b3bae0c5f0a962bad74b7107",
"https://deno.land/x/vento@v0.9.1/deps.ts": "1fb4acd6b3b6261c308280b09e8feadac7b0fac1e01bd0e0f1e75527a2181a52",
"https://deno.land/x/vento@v0.9.1/mod.ts": "ab690911075158ee3762bd7aefe209cdcb6ead7b492f14b0693d7025244db8e6",
"https://deno.land/x/vento@v0.9.1/plugins/echo.ts": "f7c064fb6d34b29852f46f6e01583ed87656dcbbc5cae51c8f29198d6951d0cf",
"https://deno.land/x/vento@v0.9.1/plugins/escape.ts": "8115ec84c84c13811f4a43263b8954e912df94df6565d6ff9ce7faea7daa50be",
"https://deno.land/x/vento@v0.9.1/plugins/export.ts": "ef54811ed0205aaeef6ad09557c94b8ae98e1457234898da5a1c5461a7dcf424",
"https://deno.land/x/vento@v0.9.1/plugins/for.ts": "6313e139a23ed17ca8b0852031f8d9e11aeb7520b228e68b9233418d25745414",
"https://deno.land/x/vento@v0.9.1/plugins/function.ts": "cdf610a98493e4a093c53473abdad7d47cbcff40aa8362d280e39910620cb8d6",
"https://deno.land/x/vento@v0.9.1/plugins/if.ts": "9de295f8675cacaec7866ad21068b6b089bfcadf72d3c62e1df50ca378c04279",
"https://deno.land/x/vento@v0.9.1/plugins/import.ts": "406204ab9d785db206da5d5cbcffa9a111cef2a39a19574e630cdea89b0691c5",
"https://deno.land/x/vento@v0.9.1/plugins/include.ts": "a9c65ce90354766220c0c9f7b21ea2db97bed99d9ffbe28f8a5ac035d488b163",
"https://deno.land/x/vento@v0.9.1/plugins/js.ts": "2c50d60061e9c5b6280a145266e617181534b8767e91127d59d5cf5febdcfb03",
"https://deno.land/x/vento@v0.9.1/plugins/layout.ts": "b9970b762ba73cf5605e63e585792803a48e326621c6cb2ec216502ba21a90cd",
"https://deno.land/x/vento@v0.9.1/plugins/set.ts": "016235a906f99cbfab78d29dfdfe8ca0925db7a46458fd873adacd0d7c6ed82d",
"https://deno.land/x/vento@v0.9.1/plugins/unescape.ts": "946512835a409815d6ad98ac4529440e9a368f42ca499791d0f25ee0ecc4c4d6",
"https://deno.land/x/vento@v0.9.1/src/environment.ts": "9c28fbf05176297adb93fc688711125b295c69089554d4211cd38a5b04028ec5",
"https://deno.land/x/vento@v0.9.1/src/loader.ts": "eb01b0dca7ea8bcdcdfd30b1f90f2fad28fb7f2cfd943900322a85bfaa86130c",
"https://deno.land/x/vento@v0.9.1/src/tokenizer.ts": "e9918ac58f941e048fe08cea10e65fb6e19c00fe7ed31fb050663445f11c6e9d",
"https://esm.sh/lodash-es@4.17.21": "460848e64379750386465df2bfcbe530dc5be584cabb39816e0dec105e5f9af2",
"https://esm.sh/v135/lodash-es@4.17.21/denonext/lodash-es.mjs": "ca6d37e6a1271d1bd8920da5ff11f7d05465f5d7961d5d09b44db331838981d7"
}
}
Executable
+1
View File
@@ -0,0 +1 @@
exec deno run -A https://deno.land/x/deploy/deployctl.ts deploy --prod --project=phenix server.ts
BIN
View File
Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.4 KiB

Generated
+60
View File
@@ -0,0 +1,60 @@
{
"nodes": {
"flake-utils": {
"inputs": {
"systems": "systems"
},
"locked": {
"lastModified": 1710146030,
"narHash": "sha256-SZ5L6eA7HJ/nmkzGG7/ISclqe6oZdOZTNoesiInkXPQ=",
"owner": "numtide",
"repo": "flake-utils",
"rev": "b1d9ab70662946ef0850d488da1c9019f3a9752a",
"type": "github"
},
"original": {
"owner": "numtide",
"repo": "flake-utils",
"type": "github"
}
},
"nixpkgs": {
"locked": {
"lastModified": 1719848872,
"narHash": "sha256-H3+EC5cYuq+gQW8y0lSrrDZfH71LB4DAf+TDFyvwCNA=",
"owner": "NixOS",
"repo": "nixpkgs",
"rev": "00d80d13810dbfea8ab4ed1009b09100cca86ba8",
"type": "github"
},
"original": {
"id": "nixpkgs",
"ref": "nixos-unstable",
"type": "indirect"
}
},
"root": {
"inputs": {
"flake-utils": "flake-utils",
"nixpkgs": "nixpkgs"
}
},
"systems": {
"locked": {
"lastModified": 1681028828,
"narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=",
"owner": "nix-systems",
"repo": "default",
"rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e",
"type": "github"
},
"original": {
"owner": "nix-systems",
"repo": "default",
"type": "github"
}
}
},
"root": "root",
"version": 7
}
+32
View File
@@ -0,0 +1,32 @@
{
description = "Phenix website";
inputs = {
nixpkgs.url = "nixpkgs/nixos-unstable";
flake-utils.url = "github:numtide/flake-utils";
};
outputs = { self, nixpkgs, flake-utils }:
flake-utils.lib.eachDefaultSystem (system:
let
pkgs = nixpkgs.legacyPackages.${system};
build-static-files = pkgs.stdenv.mkDerivation {
name = "phenix-website-static-assets";
src = ./static;
buildPhase = ''
find . -type f -exec ${pkgs.brotli}/bin/brotli -9 -f -k {} \;
'';
installPhase = ''
cp -r . $out
'';
};
in {
packages = { static = build-static-files; };
devShell = pkgs.mkShell {
name = "Phenix-Website";
buildInputs = with pkgs; [ deno ];
};
});
}
-105
View File
@@ -1,105 +0,0 @@
var gulp = require('gulp');
var bower = require('gulp-bower');
var help = require('gulp-task-listing');
var clean = require('gulp-clean');
var toml = require('gulp-toml');
var sass = require('gulp-sass');
var rename = require("gulp-rename");
var yaml = require('gulp-yaml');
var template = require('gulp-template');
var wrapper = require('gulp-wrapper');
var rename = require("gulp-rename");
var webserver = require('gulp-webserver');
var marked = require('marked');
var _ = require('lodash');
gulp.task('help', help);
gulp.task('bower', function(){
return bower()
.pipe(gulp.dest('lib/'))
.on('error', console.log);
});
gulp.task('sass', ['bower'], function(){
var extraSassPath = ['./lib/'];
return gulp.src('./scss/*.scss')
.pipe(sass({includePaths: extraSassPath}).on('error', console.log))
.pipe(gulp.dest('./css'));
});
gulp.task('clean', function(){
return gulp.src(["lib/", "css/"], {read: false})
.pipe(clean());
});
gulp.task('compile-results', function(){
return gulp.src('data/*.yaml')
.pipe(yaml({safe: true}))
.pipe(gulp.dest('./api'));
});
gulp.task('template-prod', function () {
return gulp.src('index.tmpl.html')
.pipe(rename("index.html"))
.pipe(template({production: true}))
.pipe(gulp.dest('.'));
});
gulp.task('template-dev', function () {
return gulp.src('index.tmpl.html')
.pipe(rename("index.html"))
.pipe(template({production: false}))
.pipe(gulp.dest('.'));
});
gulp.task('compile-articles', function(){
var transformArticle = function(article){
var isMarkdownKey = /markdown/i;
_.each(article, function(section, sectionName){
_.each(section, function(value, key){
if(isMarkdownKey.test(key) && _.isString(value)){
section[key] = marked(value);
}
});
});
return JSON.stringify(article, null, 4);
};
gulp.src('data/articles/**/*.toml.md')
.pipe(toml({to: transformArticle}))
.pipe(wrapper({
header: "define(['m', '_'], function (m, _ ) {\nreturn ",
footer: ';\n});\n'
}))
.pipe(rename(function(path){
path.basename = path.basename.replace(/\.toml$/i, '');
path.extname = '.js';
return path;
}))
.pipe(gulp.dest('./script/articles/'));
});
gulp.task('default', ['bower', 'sass', 'compile-results', 'compile-articles']);
gulp.task('prod', ['default', 'template-prod']);
gulp.task('webserver', function(){
return gulp.src('.')
.pipe(webserver({
host: '0.0.0.0',
port: 2222,
livereload: false,
directoryListing: false,
}));
});
gulp.task('dev', ['default', 'webserver', 'template-dev', 'bower'], function(){
gulp.watch('./scss/*.scss', ['sass']);
gulp.watch('*.tmpl.html', ['template-dev']);
gulp.watch('./data/articles/**/*', ['compile-articles']);
return gulp.watch('./data/*.yaml', ['compile-results']);
});
Binary file not shown.

Before

Width:  |  Height:  |  Size: 68 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 145 KiB

-19
View File
@@ -1,19 +0,0 @@
<!doctype html>
<html>
<head>
<meta charset="utf-8" >
<title>Balle Phenix</title>
<link rel="shortcut icon" href="/favicon.ico">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="css/style.css" />
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/font-awesome/4.5.0/css/font-awesome.min.css">
</head>
<body>
<%if(production){ %>
<script src="main-built.js"></script>
<% }else{ %>
<script data-main="script/main" src="lib/requirejs/require.js"></script>
<% } %>
</body>
</html>
+1
View File
@@ -0,0 +1 @@
hello {{ title }}
-18
View File
@@ -1,18 +0,0 @@
0 info it worked if it ends with ok
1 verbose cli [ '/usr/bin/node', '/usr/bin/npm', 'install' ]
2 info using npm@1.4.28
3 info using node@v0.10.37
4 verbose node symlink /usr/bin/node
5 error install Couldn't read dependencies
6 error package.json ENOENT, open '/home/didier/dev/go/src/gitlab.com/didiercrunch/phenix-website/static/package.json'
6 error package.json This is most likely not a problem with npm itself.
6 error package.json npm can't find a package.json file in your current directory.
7 error System Linux 4.2.0-23-generic
8 error command "/usr/bin/node" "/usr/bin/npm" "install"
9 error cwd /home/didier/dev/go/src/gitlab.com/didiercrunch/phenix-website/static
10 error node -v v0.10.37
11 error npm -v 1.4.28
12 error path /home/didier/dev/go/src/gitlab.com/didiercrunch/phenix-website/static/package.json
13 error code ENOPACKAGEJSON
14 error errno 34
15 verbose exit [ 34, true ]
-34
View File
@@ -1,34 +0,0 @@
{
"name": "phenix-website",
"version": "1.0.0",
"description": "Main web site of Balle Phénix.",
"main": "index.html",
"dependencies": {
"gulp": "^3.9.0",
"gulp-bower": "0.0.13",
"gulp-clean": "^0.3.1",
"gulp-rename": "^1.2.2",
"gulp-sass": "^2.1.1",
"gulp-task-listing": "^1.0.1",
"gulp-template": "^3.1.0",
"gulp-toml": "^0.1.1",
"gulp-wrap": "^0.11.0",
"gulp-wrapper": "^1.0.0",
"lodash": "^4.6.1",
"marked": "^0.3.5",
"requirejs": "^2.1.22"
},
"devDependencies": {
"gulp-webserver": "^0.9.1",
"gulp-yaml": "^1.0.1"
},
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"repository": {
"type": "git",
"url": "https://gitlab.com/didiercrunch/phenix-website"
},
"author": "didier amyot <didier.amyot@gmail.com>",
"license": "MIT"
}
-16
View File
@@ -1,16 +0,0 @@
define(['m', 'articles/inscription'], function (m, inscription) {
var simplifyArticleStructure = function(article){
var ret = {};
_.each(article, function(section, sectionName){
ret[sectionName] = m.trust(section.innerMarkdown);
});
return ret;
};
var articles = [];
articles.push(inscription);
return _.map(articles, simplifyArticleStructure);
});
-20
View File
@@ -1,20 +0,0 @@
requirejs.config({
paths: {
'_': '../lib/lodash/dist/lodash.min',
'm': '../lib/mithril/mithril.min'
}
});
requirejs(['m', 'views/mainPage', 'views/newsPage', 'views/calendarPage', 'views/rulesPage', 'views/photosPage', 'views/confidentialPage', 'views/contactPage', 'views/loginPage',], function(m, mainPage, newsPage, calendarPage, rulesPage, photosPage, confidentialPage, contactPage, loginPage){
m.route.mode = "hash";
m.route(document.body, "/", {
"/": mainPage,
"/nouvelles": newsPage,
"/calendrier": calendarPage,
"/reglement": rulesPage,
"/photos": photosPage,
"/membre": confidentialPage,
"/contact": contactPage
});
});
-111
View File
@@ -1,111 +0,0 @@
define(['_'], function(_) {
var resultParser = {};
resultParser._addJSDateToResult = function(res){
var date = res.date.split('/');
var time = _.isString(res.time) ? res.time.split(':'): [0, 0];
res.jsDate = new Date(
Number(date[0]),
Number(date[1]) - 1,
Number(date[2]),
Number(time[0]),
Number(time[1])
);
return res;
};
resultParser.parseResults = function(rawResults){
rawResults = _.map(rawResults, resultParser._addJSDateToResult);
rawResults = _.map(rawResults, resultParser._addCustomStyle);
return rawResults;
};
resultParser.getNightGames = function(rawResults){
var ret = {};
_.each(resultParser.parseResults(rawResults), function(res){
if(_.has(ret, res.date)){
ret[res.date].push(res);
}else{
ret[res.date] = [res];
}
});
return _.map(ret, function(games, date){
return resultParser._addJSDateToResult({date: date, games: games});
});
};
resultParser._getAllTeams = function(rawResults){
var homeTeams = _.map(rawResults, 'home');
var awayTeams = _.map(rawResults, 'away');
return _.uniq(_.concat(homeTeams, awayTeams));
};
resultParser._getWinner = function(res){
if(res.home_points > res.away_points){
return res.home;
}
if(res.home_points < res.away_points){
return res.away;
}
};
resultParser._hasWon = function(res, team){
return resultParser._getWinner(res) == team;
};
resultParser._hasLost = function(res, team){
return !resultParser._isDraw(res) && resultParser._getWinner(res) != team;
};
resultParser._isDraw = function(res){
return res.home_points == res.away_points;
};
resultParser._getPointsFor = function(res, team){
if(res.home == team){
return res.home_points;
}
return res.away_points;
};
resultParser._getPointsForOpponent = function(res, team){
if(res.home == team){
return res.away_points;
}
return res.home_points;
};
resultParser._getPointsForGame = function(res, team){
if(resultParser._hasWon(res, team)){
return 2;
}
return resultParser._isDraw(res) ? 1: 0;
};
resultParser._getTeamStats = function(rawResults, team){
var ret = {
team: team, gamePlayed: 0, victories: 0, points: 0,
defeats: 0, draws: 0, pointsFor: 0, pointsAgaint: 0};
_.each(rawResults, function(res){
if((team != res.home && team != res.away) || !_.isNumber(res.home_points)){
return;
}
ret.gamePlayed += 1;
ret.victories += resultParser._hasWon(res, team) ? 1: 0;
ret.defeats += resultParser._hasLost(res, team) ? 1: 0;
ret.draws += resultParser._isDraw(res) ? 1: 0;
ret.pointsFor += resultParser._getPointsFor(res, team);
ret.pointsAgaint += resultParser._getPointsForOpponent(res, team);
ret.points += resultParser._getPointsForGame(res, team);
});
return ret;
};
resultParser.getStats = function(rawResults){
var allTeams = resultParser._getAllTeams(rawResults);
var getTeamStats = _.partial(resultParser._getTeamStats, rawResults);
return _.map(allTeams, getTeamStats);
};
return resultParser;
});
-22
View File
@@ -1,22 +0,0 @@
define(['m', '_'], function (m, _) {
var teams = {};
teams.getTeamColor = function(teamName){
if(teamName == 'jaune'){
return '#FF0';
}
if(teamName == 'rouge'){
return '#F00';
}
if(teamName == 'bleu'){
return '#00F';
}
if(teamName == 'gris'){
return '#808080';
}
return undefined;
};
return teams;
});
-48
View File
@@ -1,48 +0,0 @@
define(['m'], function(m) {
var util = {};
util.loremIpsum = function(n){
var loremIpsum = "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Donec a"+
" diam lectus. Sed sit amet ipsum mauris. Maecenas congue ligula "+
"ac quam viverra nec consectetur ante hendrerit. Donec et mollis"+
" dolor. Praesent et diam eget libero egestas mattis sit amet"+
" vitae augue. Nam tincidunt congue enim, ut porta lorem lacinia "+
"consectetur. Donec ut libero sed arcu vehicula ultricies a non"+
" tortor. Lorem ipsum dolor sit amet, consectetur adipiscing "+
"elit. Aenean ut gravida lorem. Ut turpis felis, pulvinar a "+
"semper sed, adipiscing id dolor. Pellentesque auctor nisi id "+
"magna consequat sagittis. Curabitur dapibus enim sit amet elit "+
"pharetra tincidunt feugiat nisl imperdiet. Ut convallis libero "+
"in urna ultrices accumsan. Donec sed od";
loremIpsum = loremIpsum.split(' ');
n = n || loremIpsum.length;
return loremIpsum.splice(0, n).join(" ");
};
util.formatDate = function(date){
var monthNames = ['janvier', 'février', 'mars', 'avril', 'mai', 'juin',
'juiller', 'août', 'septembre', 'octobre', 'novembre',
'decembre'];
return [date.getDate(),
monthNames[date.getMonth()],
date.getFullYear()].join(' ');
};
util.formatDateSmall = function(date){
var smallMonthNames = ['janv', 'févr', 'mars', 'avr', 'mai', 'juin',
'juill', 'août', 'sept', 'oct', 'nov',
'dec'];
return [date.getDate(),
smallMonthNames[date.getMonth()],
date.getFullYear() % 1000].join(' ');
};
util.facebookLink = function(){
return m('a[href="https://www.facebook.com/LigueDeBalleLesPhenix"]',
m('i.fa.fa-facebook-square')
);
};
return util;
});
-136
View File
@@ -1,136 +0,0 @@
define(['m', '_', 'util', 'resultParser', 'teams', 'views/topNavBar', 'views/footer', 'images/rain.svg'], function(m, _, util, resultParser, teams, topNavBar, footer, rainSvg) {
var statsView = {};
statsView.controller = function(){
var games = m.prop([]);
return m.request({method: "GET", url: "api/resultats.json"})
.then(games)
.then(resultParser.getStats);
};
statsView.getStatRow = function(teamStats){
var formatStat = function(n){
return teamStats.gamePlayed === 0 ? '-' : n;
};
return m('tr', [
m('td', teamStats.team),
m('td', teamStats.gamePlayed),
m('td', formatStat(teamStats.victories)),
m('td', formatStat(teamStats.defeats)),
m('td', formatStat(teamStats.draws)),
m('td', formatStat(teamStats.pointsFor)),
m('td', formatStat(teamStats.pointsAgaint)),
m('td', formatStat(teamStats.pointsFor - teamStats.pointsAgaint)),
m('td', formatStat(teamStats.points))
]);
};
statsView.mainTable = function(stats){
return m('table.uk-table.uk-table-hover.uk-table-striped',[
m('thead', m('tr', [
m('th', 'Équipes'),
m('th', 'PJ'),
m('th', 'V'),
m('th', 'D'),
m('th', 'N'),
m('th', 'PP'),
m('th', 'PC'),
m('th', 'DIF'),
m('th', 'PTS')
])),
m('tbody', _.map(stats, statsView.getStatRow))
]);
};
statsView.legend = function(){
var items = ["PJ : Parties joués", "V : Victoire", "D : Défaite",
"N : Nul", "PP : Points pour", "PC : Points contre",
"DIF : Diférenciel","PTS : Points"];
return m('ul.uk-subnav.uk-subnav-line.uk-flex-center',[
_.map(items, function(itm){
return m('li', itm);
})
]);
};
statsView.view = function(stats){
return m('div.uk-grid',
m('div.uk-width-medium-1-1.uk-width-large-1-1.uk-container-center',[
m('h2', 'Classement 2016'),
statsView.mainTable(stats()),
statsView.legend()
]));
};
var schedulView = {};
schedulView.controller = function(){
var games = m.prop([]);
return m.request({method: "GET", url: "api/resultats.json"})
.then(games)
.then(resultParser.getNightGames);
};
schedulView._getTeamTag = function(teamName){
var teamColor = teams.getTeamColor(teamName);
return [
m('i.fa.fa-flag', {style: {color: teamColor}}),
m('span', ' ' + teamName)
];
};
schedulView._asGamePoints = function(points){
return !_.isNumber(points) ? '-' : points + '';
};
schedulView._gameName = function(game){
if(game.rain){
return [rainSvg('1.5em'), " ", game.time];
}
return [game.time, " ", m('span', {style: {visibility: 'hidden'}}, rainSvg('1.5em'))];
};
schedulView._gameRow = function(game){
return m('tr',[
m('td', schedulView._gameName(game)),
m('td', schedulView._getTeamTag(game.home)),
m('td', schedulView._asGamePoints(game.home_points)),
m('td', 'vs'),
m('td', schedulView._getTeamTag(game.away)),
m('td', schedulView._asGamePoints(game.away_points))
]);
};
schedulView._gameView = function(gameNight){
return m('div', [m('h3', util.formatDate(gameNight.jsDate)),
m('table.uk-table.uk-table-hover.uk-table-condensed.uk-table-striped',
m('tbody',[
_.map(gameNight.games, schedulView._gameRow),
])
)
]);
};
schedulView.view = function(games){
return m('div.uk-grid',
m('div.uk-width-large-3-5.uk-width-medium-1-1',
_.concat([m('h2', 'Calendrier 2016')], _.map(games(), schedulView._gameView))));
};
calendarPage = {};
calendarPage.view = function(){
return [m.component(topNavBar),
m('div.uk-grid.uk-margin-top.uk-margin-bottom',
m('div.uk-width-large-3-5.uk-width-medium-4-5.uk-width-small-1-1.uk-container-center',[
m.component(statsView),
m.component(schedulView)])),
m.component(footer)];
};
return calendarPage;
});
-293
View File
@@ -1,293 +0,0 @@
define(['m', '_', 'teams', 'views/topNavBar', 'views/footer'], function (m, _ , teams, topNavBar, footer) {
var confidentialSelection = {};
confidentialSelection.toggleTeam = function(teamId, activatedTeams){
return function(isActive){
isActive = isActive != 'true';
if(isActive){
activatedTeams().push(teamId);
return;
}
activatedTeams(_.difference(activatedTeams(), [teamId]));
};
};
confidentialSelection.teamInput = function(teamName, teamId, activatedTeams){
var isActive = _.includes(activatedTeams(), teamId);
var class_ = isActive ? 'uk-badge-success' : '';
var callback = confidentialSelection.toggleTeam(teamId, activatedTeams);
return m('div.uk-badge.uk-margin-left.uk-border-rounded',
{class: class_, 'data-selected': isActive, onclick: m.withAttr("data-selected", callback)},
m('h3', {style: {width: '80px'}}, teamName)
);
};
confidentialSelection.scoreInput = function(score, activatedScores){
var isActive = _.includes(activatedScores(), score);
var class_ = isActive ? 'uk-badge-success' : '';
var callback = confidentialSelection.toggleTeam(score, activatedScores);
return m('div.uk-badge.uk-margin-left.uk-border-rounded',
{class: class_, 'data-selected': isActive, onclick: m.withAttr("data-selected", callback)},
m('h3', {style: {width: '80px'}}, score)
);
};
confidentialSelection.chooseTeams = function(model){
return m('form.uk-grid', {style: {'margin-top': '1em'}},
m('div.uk-width-1-6', m('label', m('b', 'Équipes'))),
m('div.uk-width-5-6',
m('div.uk-grid', [
confidentialSelection.teamInput('Bleu', 'bleu', model.activatedTeams),
confidentialSelection.teamInput('Rouge', 'rouge', model.activatedTeams),
confidentialSelection.teamInput('Jaune', 'jaune', model.activatedTeams),
confidentialSelection.teamInput('Gris', 'gris', model.activatedTeams),
]))
);
};
confidentialSelection.chooseScore = function(model){
return m('form.uk-grid', {style: {'margin-top': '1em'}},
m('div.uk-width-1-6', m('label', m('b', 'Score'))),
m('div.uk-width-5-6',
m('div.uk-grid', [
confidentialSelection.scoreInput(1, model.activatedScores),
confidentialSelection.scoreInput(2, model.activatedScores),
confidentialSelection.scoreInput(3, model.activatedScores),
confidentialSelection.scoreInput(4, model.activatedScores),
confidentialSelection.scoreInput(5, model.activatedScores)
]))
);
};
confidentialSelection.controller = function(model){
return model;
};
confidentialSelection.view = function(model){
return m('div', [
confidentialSelection.chooseTeams(model),
confidentialSelection.chooseScore(model)
]);
};
var confidentialTable = {};
confidentialTable._sortFunction = function(sortingElm){
};
confidentialTable._sortPlayers = function(sorting, playerList){
var sortingKeys = _.map(sorting(), 'key');
var sortingDirections = _.map(sorting(), function(o){
return o.direction == 1 ? 'desc' : 'asc';
});
return _.orderBy(playerList, sortingKeys, sortingDirections);
};
confidentialTable.controller = function(model){
var players = m.prop([]);
var ctrl = {};
ctrl.model = model;
ctrl.players = m.request({method: "GET", url: "api/players.json"})
.then(players);
ctrl.sortPlayers = function(){
ctrl.players(confidentialTable._sortPlayers(ctrl.model.sorting, ctrl.players()));
};
return ctrl;
};
confidentialTable._getSortDict = function(sorting){
var ret = {};
_.each(sorting(), function(elm){
ret[elm.key] = elm.direction;
});
return ret;
};
confidentialTable._isSortingUp = function(sorting, key){
var dict = confidentialTable._getSortDict(sorting);
return dict[key] === 1;
};
confidentialTable._isSortingDown = function(sorting, key){
var dict = confidentialTable._getSortDict(sorting);
return dict[key] === -1;
};
confidentialTable.arrows = function(sorting, key){
var sortUp = confidentialTable._isSortingUp(sorting, key);
var sortDown = confidentialTable._isSortingDown(sorting, key);
var style = {
display: 'inline-block',
'line-height': '0.5em',
'margin-right': '1em',
'font-size': '0.7em'
};
var sortedStyle = {color: '#8cc14c', 'font-weight': 'bold'};
return m('span', {style: style},
m('i.fa.fa-chevron-up', {style: sortUp ? sortedStyle: {}}),
m('br'),
m('i.fa.fa-chevron-down', {style: sortDown ? sortedStyle: {}})
);
};
confidentialTable._setSorting = function(sorting, key){
var newDirection = {key: key, direction: -1 * confidentialTable._getSortDict(sorting)[key]};
var directions = _.filter(sorting(), function(o){
return o.key != key;
});
sorting([newDirection].concat(directions));
};
confidentialTable.tableHeader = function(sorting){
var setSorting = function(key){
return _.partial(confidentialTable._setSorting, sorting, key);
};
return m('thead',
m('tr', [
m('th', {onclick: setSorting('team')}, confidentialTable.arrows(sorting, 'team'), 'Équipe'),
m('th', {onclick: setSorting('name')}, confidentialTable.arrows(sorting, 'name'), 'Nom'),
m('th.uk-hidden-small', 'Courriel'),
m('th.uk-hidden-small', 'Téléphone'),
m('th', {onclick: setSorting('score')}, confidentialTable.arrows(sorting, 'score'), 'Cote')
]));
};
confidentialTable.getPlayerTeamIcon = function(player){
var background = teams.getTeamColor(player.team);
var style = {width: '20px', height: '20px', 'background-color': background};
return m('div', {style: style}, m.trust('&nbsp;'));
};
confidentialTable.playerRow = function(player){
return m('tr',[
m('td', confidentialTable.getPlayerTeamIcon(player)),
m('td', player.name),
m('td.uk-hidden-small', player.email),
m('td.uk-hidden-small', player.tel),
m('td', player.score)
]);
};
confidentialTable.onlyPlayerOfTeam = function(visibleTeam){
return function(player){
return _.includes(visibleTeam, player.team);
};
};
confidentialTable.onlyPlayerOfScore = function(visibleScores){
return function(player){
return _.includes(visibleScores, player.score);
};
};
confidentialTable.tableBody = function(players, visibleTeam, activatedScores){
return m('tbody',
_(players)
.filter(confidentialTable.onlyPlayerOfTeam(visibleTeam))
.filter(confidentialTable.onlyPlayerOfScore(activatedScores))
.map(confidentialTable.playerRow).value()
);
};
confidentialTable.view = function(ctrl){
ctrl.sortPlayers();
return m('table.uk-table.uk-table-hover.uk-table-striped',
confidentialTable.tableHeader(ctrl.model.sorting),
confidentialTable.tableBody(ctrl.players(),
ctrl.model.activatedTeams(),
ctrl.model.activatedScores()
)
);
};
var confidentialPageBody = {};
confidentialPageBody.controller = function(){
var model = {};
model.activatedTeams = m.prop(['bleu', 'rouge', 'jaune', 'gris']);
model.activatedScores = m.prop([1, 2, 3, 4, 5]);
model.sorting = m.prop([{key: 'team', direction: 1}, {key: 'score', direction: -1}, {key: 'name', direction: 1}]);
return model;
};
confidentialPageBody.view = function(model){
return m('div.uk-grid.uk-margin-top.uk-margin-bottom',
m('div.uk-width-large-3-5.uk-width-small-1-1.uk-container-center', [
m.component(confidentialSelection, model),
m.component(confidentialTable, model),
]));
};
var loginComponent = {};
loginComponent.controller = function(){
return {email: m.prop(), password: m.prop()};
};
loginComponent.logo = function(){
var style = 'height: 250px; width: 250px; background-size: 250px; background-image: url(images/logosansfond.JPG);';
return m('div.uk-cover-background.uk-container-center', {style: style});
};
loginComponent.logoLine = function(){
return m('div.uk-grid.uk-margin',
m('div.uk-width-1-1', loginComponent.logo()));
};
loginComponent.login = function(ctrl){
return function(){
var salt = "9'D)E@E{DSq[|l2bq!v";
window.secret = salt + ctrl.email() + ctrl.password();
};
};
loginComponent.loginForm = function(ctrl){
return m('div.uk-panel.uk-panel-box.uk-panel-box-secondary.uk-width-large-1-3.uk-container-center.uk-margin', [
m('form.uk-text-center', {onsubmit: m.withAttr("form", loginComponent.login(ctrl))},
m('div.uk-form-row',
m('label', "Nom d'utilisateur ",
m('input[type=text][required].uk-form-width-small', {oninput: m.withAttr("value", ctrl.email)}))),
m('div.uk-form-row',
m('label', "Mot de passe ",
m('input[type=password][required].uk-form-width-small', {oninput: m.withAttr("value", ctrl.password)}))),
m('div.uk-form-row', m('button.uk-button', m("i.fa.fa-mars-double"), " Pénétrez"))
)
]);
};
loginComponent.view = function(ctrl){
return m('div', [
loginComponent.logoLine(),
loginComponent.loginForm(ctrl)
]);
};
var confidentialPage = {};
confidentialPage.view = function(){
var body;
window.secret = 'o'
if(!window.secret){
body = loginComponent;
}else{
body = confidentialPageBody;
}
return [
m.component(topNavBar),
m.component(body),
m.component(footer)
];
};
return confidentialPage;
});
-67
View File
@@ -1,67 +0,0 @@
define(['m', '_', 'util', 'resultParser', 'views/topNavBar', 'views/footer'], function (m, _ , util, resultParser, topNavBar, footer) {
var contactBody = {};
contactBody.logo = function(){
var style = 'height: 300px; width: 300px; background-size: 300px; background-image: url(images/logosansfond.JPG);';
return m('div.uk-cover-background.uk-container-center', {style: style});
};
contactBody.logoLine = function(){
return m('div.uk-grid.uk-margin',
m('div.uk-width-1-1', contactBody.logo()));
};
contactBody.email = function(){
return m('a[href=mailto:info@ballephenix.com]', 'info@ballephenix.com');
};
contactBody.tel = function(){
return ' (514) 544-8976';
};
contactBody.address = function(){
return m('p', ' 123 rue Dufresne', m('br'), 'Montréal, Québec H6Y 8U7');
};
contactBody.contact = function(){
return m('div.div.uk-panel.uk-panel-box.uk-panel-box-secondary.uk-container-center.uk-margin',[
m('table.uk-table',
m('tr',
m('td.uk-text-right', m('i.fa.fa-desktop')),
m('td', contactBody.email())
),
m('tr',
m('td.uk-text-right', m('i.fa.fa-phone')),
m('td', contactBody.tel())
),
m('tr',
m('td.uk-text-right', m('i.fa.fa-envelope')),
m('td', contactBody.address())
)
)
]);
};
contactBody.view = function(){
return m('div.uk-margin-top.uk-margin-bottom.uk-grid',
m('div.uk-width-large-2-5.uk-width-medium-4-5.uk-width-small-1-1.uk-container-center', [
contactBody.logoLine(),
contactBody.contact()
])
);
};
var contactPage = {};
contactPage.view = function(){
return [
m.component(topNavBar),
m.component(contactBody),
m.component(footer)
];
};
return contactPage;
});
-23
View File
@@ -1,23 +0,0 @@
define(['m', '_', 'util'], function (m, _, util) {
var footer = {};
footer.wording = function(){
return [
m('span.uk-hidden-small', 'Ligue de balle les Phénix... pour le plaisir de jouer!'),
m('h4.uk-visible-small', 'Ligue de balle les Phénix')
];
};
footer.view = function(){
return m('footer.uk-grid.ph-footer', {style: {padding: '40px'}},
m('div.uk-container.uk-container-center.uk-text-center', [
m('div.uk-panel', footer.wording()),
m('ul.uk-subnav.uk-subnav-line.uk-flex-center',
m('li', m('a[href="mailto:info@ballephenix.com"]', 'info@ballephenix.com'))),
m('h1', util.facebookLink())
])
);
};
return footer;
});
-43
View File
@@ -1,43 +0,0 @@
define(['m', '_', 'util', 'views/topNavBar', 'views/footer'], function (m, _ , util, topNavBar, footer) {
var loginComponent = {};
loginComponent.logo = function(){
var style = 'height: 250px; width: 250px; background-size: 250px; background-image: url(images/logosansfond.JPG);';
return m('div.uk-cover-background.uk-container-center', {style: style});
};
loginComponent.logoLine = function(){
return m('div.uk-grid.uk-margin',
m('div.uk-width-1-1', loginComponent.logo()));
};
loginComponent.loginForm = function(){
return m('div.uk-panel.uk-panel-box.uk-panel-box-secondary.uk-width-large-1-3.uk-container-center.uk-margin', [
m('form.uk-text-center',
m('div.uk-form-row', m('label', "Nom d'utilisateur ", m('input[type=text].uk-form-width-small'))),
m('div.uk-form-row', m('label', "Mot de passe ", m('input[type=password].uk-form-width-small'))),
m('div.uk-form-row', m('button.uk-button', m("i.fa.fa-mars-double"), " Pénétrez"))
)
]);
};
loginComponent.view = function(){
return m('div', [
loginComponent.logoLine(),
loginComponent.loginForm()
]);
};
var loginPage = {};
loginPage.view = function(){
return [
m.component(topNavBar),
m.component(loginComponent),
m.component(footer)
];
};
return loginPage;
});
-169
View File
@@ -1,169 +0,0 @@
define(['m', '_', 'util', 'resultParser', 'views/topNavBar', 'views/footer', 'articles/articles'], function (m, _ , util, resultParser, topNavBar, footer, articles) {
var mainPageLogo = {};
mainPageLogo.view = function(){
return m('div.uk-grid', [
m('div.uk-large-1-3.uk-medium-2-3.uk-container-center', [
m('div.uk-cover-background.uk-container-center.uk-margin-left.uk-margin-top',{style: 'height:300px; width: 300px; background-size: 300px; background-image: url(images/logosansfond.JPG);'})
])
]);
};
var mainPageNews = {};
mainPageNews.view = function(){
var article = _.get(articles, 0, {});
return m('div.uk-panel.uk-panel-box',[
m('div.uk-panel-badge.uk-badge', [
m('i.fa.fa-newspaper-o')
]),
m('h3.uk-panel-title', m('a.uk-link-muted', {href: '#/nouvelles'}, article.title)),
m('p', article.smallBody || article.body)
]);
};
var nextGameDaySchedule = {};
nextGameDaySchedule.controller = function(){
var games = m.prop([]);
return m.request({method: "GET", url: "api/resultats.json"})
.then(games)
.then(resultParser.getNightGames)
.then(function(nightGames){
return nightGames[0].games;
});
};
nextGameDaySchedule._getTableHead = function(){
return m('thead', m('tr', [
m('td', 'Date'),
m('td', 'Heure'),
m('td', 'Visiteur'),
m('td', 'Receveur')
]));
};
nextGameDaySchedule._responsoveText = function(largeText, smallText){
return [m('span.uk-visible-large', largeText),
m('span.uk-hidden-large', smallText)];
};
nextGameDaySchedule._getGamesRow = function(game){
return m('tr', [
m('td', nextGameDaySchedule._responsoveText(util.formatDate(game.jsDate),
util.formatDateSmall(game.jsDate))),
m('td', game.time),
m('td', game.away),
m('td', game.home)
]);
};
nextGameDaySchedule._getGamesRows = function(games){
return _.map(games(), nextGameDaySchedule._getGamesRow);
};
nextGameDaySchedule.view = function(games){
return m('table.uk-table.uk-table-hover.uk-table-striped.uk-table-condensed',[
nextGameDaySchedule._getTableHead(),
m('tbody',
nextGameDaySchedule._getGamesRows(games)
)]);
};
var mainPageSchedule = {};
mainPageSchedule.view = function(){
return m('div.uk-panel.uk-panel-box',[
m('div.uk-panel-badge.uk-badge', m('i.fa.fa-clock-o')),
m('h3.uk-panel-title', m('a.uk-link-muted', {href: '#/calendrier'}, 'Horaire')),
m.component(nextGameDaySchedule)
]);
};
var mainMap = {};
mainMap.getMap = function(){
var iframeUrl = "//www.openstreetmap.org/export/embed.html?bbox=-73.55889558792114%2C45.53089890181621%2C-73.55181455612183%2C45.53426212742867&amp;layer=mapnik";
var externalLink = "http://www.openstreetmap.org/#map=18/45.53258/-73.55536";
var iframeParams = {
style: {border: '1px solid black', 'min-height': '300px'},
width: '100%',
// height: '100%',
frameborder: 0,
scrolling: 'no',
marginheight: 0,
src: iframeUrl
};
return [
m('iframe', iframeParams),
m('br'),
m('small', m('a', {href: externalLink}, 'Voir la carte'))
];
};
mainMap.view = function(){
return m('div.uk-panel.uk-panel-box',[
m('div.uk-panel-badge.uk-badge', [
m('i.fa.fa-map-o')
]),
m('h3.uk-panel-title', 'Parc Walter-Stewart'),
mainMap.getMap()
]);
};
var mainPageBottom = {};
mainPageBottom.regularSizeView = function(){
return m('div.uk-grid.uk-visible-large.uk-grid-match', [
m('div.uk-width-large-1-3.uk-width-medium-1-3', m.component(mainPageNews)),
m('div.uk-width-large-1-3.uk-width-medium-1-3', m.component(mainPageSchedule)),
m('div.uk-width-large-1-3.uk-width-medium-1-3', m.component(mainMap))
]);
};
mainPageBottom.mediumSizeView = function(){
return m('div.uk-visible-medium', [
m('div.uk-grid.uk-grid-match', [
m('div.uk-width-medium-1-2', [m.component(mainPageNews)]),
m('div.uk-width-medium-1-2', [m.component(mainPageSchedule)]),
]),
m('div.uk-grid',
m('div.uk-width-medium-1-1', m.component(mainMap))
)
]);
};
mainPageBottom.smallSizeView = function(){
return m('div.uk-visible-small',
[
m('div.uk-grid', m('div.uk-width-small-1-1', m.component(mainPageNews))),
m('div.uk-grid', m('div.uk-width-small-1-1', m.component(mainPageSchedule))),
m('div.uk-grid', m('div.uk-width-small-1-1', m.component(mainMap)))
]);
};
mainPageBottom.view = function(){
return m('div.uk-margin-top.uk-margin-bottom.uk-grid',
m('div.uk-width-large-3-5.uk-width-medium-4-5.uk-width-small-1-1.uk-container-center', [
mainPageBottom.regularSizeView(),
mainPageBottom.mediumSizeView(),
mainPageBottom.smallSizeView()
])
);
};
var mainPage = {};
mainPage.view = function(){
return [
topNavBar.view(),
mainPageLogo.view(),
mainPageBottom.view(),
footer.view()
];
};
return mainPage;
});
-36
View File
@@ -1,36 +0,0 @@
define(['m', '_', 'util', 'resultParser', 'articles/articles', 'views/topNavBar', 'views/footer'], function (m, _ , util, resultParser, articles, topNavBar, footer) {
var newsPageBody = {};
newsPageBody.logo = function(){
var style = 'height: 250px; width: 250px; background-size: 250px; background-image: url(images/logosansfond.JPG);';
return m('div.uk-cover-background.uk-container-center', {style: style});
};
newsPageBody.getArticle = function(article){
return m('article.uk-article.uk-margin-',
m('h1.uk-article-title', article.title),
m('p.uk-article-meta', article.meta),
article.body
);
};
newsPageBody.view = function(){
return m('div', _.map(articles, newsPageBody.getArticle));
};
var newsPage = {};
newsPage.view = function(){
return [
m.component(topNavBar),
m('div.uk-grid.uk-margin-top.uk-margin-bottom',
m('div.uk-width-large-2-5.uk-width-medium-3-5.uk-width-small-1-1.uk-container-center',
m.component(newsPageBody))),
m.component(footer)
];
};
return newsPage;
});
-26
View File
@@ -1,26 +0,0 @@
define(['m', '_', 'util', 'resultParser', 'views/topNavBar', 'views/footer'], function (m, _ , util, resultParser, topNavBar, footer) {
var rulesPageBody = {};
rulesPageBody.logo = function(){
var style = 'height: 250px; width: 250px; background-size: 250px; background-image: url(images/logosansfond.JPG);';
return m('div.uk-cover-background.uk-container-center', {style: style});
};
rulesPageBody.view = function(){
return m('div.uk-grid',
m('div.uk-width-1-1', rulesPageBody.logo()));
};
var photosPage = {};
photosPage.view = function(){
return [
m.component(topNavBar),
m.component(rulesPageBody),
m.component(footer)
];
};
return photosPage;
});
-63
View File
@@ -1,63 +0,0 @@
define(['m', '_', 'util', 'resultParser', 'views/topNavBar', 'views/footer'], function (m, _ , util, resultParser, topNavBar, footer) {
var rulesPage = {};
rulesPage.missionText = function(){
return "La ligue de balle Les Phénix a été fondée en 2004 afin "+
"d'offrir aux membres de la communauté gaie et lesbienne et à "+
"leurs amis hétéros l'opportunité de s'amuser et de pratiquer "+
"un sport dans une ambiance amicale et décontractée. "+
"L'ouverture d'esprit, la camaraderie et le plaisir de "+
"pratiquer un sport à l'extérieur caractérisent cette ligue.";
};
rulesPage.logo = function(){
var style = 'height: 250px; width: 250px; background-size: 250px; background-image: url(images/logosansfond.JPG);';
return m('div.uk-cover-background.uk-container-center', {style: style});
};
rulesPage.rules = function(){
var urlASBM = 'http://montreal.baseballquebec.com/fr/publication/nouvelle/recherche_un_directeur_general_asbm.html';
return m('div.uk-width-large-2-3.uk-width-small-1-1',
m('div.uk-panel.uk-panel-box.uk-panel-box-secondary', [
m('h2', 'Règlements 2016'),
m('ul',[
m('li', m('h3', m('a', {href: 'files/reglements_generaux.pdf'}, 'Règlements généraux'))),
m('li', m('h3', m('a', {href: 'files/regles_procedures2015.pdf'},'Règles et procédures'))),
m('li', m('h3', m('a', {href: 'files/reglements_de_terrain2015.pdf'},'Règlements de terrain'))),
m('li', m('h3', m('a', {href: urlASBM}, 'Association des Sports de Balle à Montréal (ASBM)'))),
])
])
);
};
rulesPage.logoAndRules = function(){
return m('div.uk-grid',[
m('div.uk-width-large-1-3.uk-width-small-1-1', rulesPage.logo()),
rulesPage.rules()
]
);
};
rulesPage.mission = function(){
return m('div.uk-panel.uk-panel-box.uk-panel-box-secondary', [
m('h2', 'Mission'),
m('p', rulesPage.missionText())
]);
};
rulesPage.view = function(){
return [
m.component(topNavBar),
m('div.uk-margin-top.uk-margin-bottom.uk-grid',
m('div.uk-width-large-3-5.uk-width-medium-4-5.uk-width-large-1-1.uk-container-center', [
rulesPage.logoAndRules(),
rulesPage.mission()
])),
m.component(footer)
];
};
return rulesPage;
});
-44
View File
@@ -1,44 +0,0 @@
define(['m', '_', 'util'], function (m, _, util) {
var topNavBar = {};
topNavBar._urlMapping = {
'': 'Accueil',
nouvelles: 'Nouvelles',
calendrier: 'Calendrier',
reglement: 'Règlement',
// photos: 'Photos',
membre: 'Membre',
contact: 'Nous Joindre'
};
topNavBar.controller = function(){
return {id: m.route.param("page")};
};
topNavBar._getUrlForId = function(id_){
return '#/' + id_;
};
topNavBar._isActive = function(id_){
return topNavBar._getUrlForId(id_) == window.location.hash;
};
topNavBar._getItem = function(name, id){
var class_ = topNavBar._isActive(id) ? 'uk-active' : 'uk-parent';
var url = topNavBar._getUrlForId(id);
return m("li", {class: class_}, [m("a",{href: url}, name)]);
};
topNavBar.view = function(controller){
return m("nav.uk-navbar.uk-navbar-attached",[
m("ul.uk-navbar-nav.uk-navbar-center.uk-visible-large",
m('li.uk-parent', m('div.uk-navbar-brand', util.facebookLink())),
_.map(topNavBar._urlMapping, topNavBar._getItem)),
m("ul.uk-navbar-nav.uk-hidden-large",
m('li.uk-parent', util.facebookLink()),
_.map(topNavBar._urlMapping, topNavBar._getItem)),
]);
};
return topNavBar;
});
-67
View File
@@ -1,67 +0,0 @@
// LESS related
@import "uikit/scss/uikit-mixins.scss";
@import "uikit/scss/core/variables.scss";
// Phenix colors
$navbar-background: #f08d28; //#dabd5e;
// $foo: ; // #f8c694;
$panel-box-background: #fce3ca;
$table-striped-background: #fce3ca;
$navbar-nav-active-background: #fce3ca;
$navbar-nav-hover-background: #fce3ca;
$panel-box-secondary-background: #fce3ca;
$badge-background: #fce3ca;
$badge-color: black;
$badge-font-size: 2em;
// Defaults
@import "uikit/scss/core/base.scss";
// Layout
@import "uikit/scss/core/grid.scss";
@import "uikit/scss/core/panel.scss";
@import "uikit/scss/core/block.scss";
@import "uikit/scss/core/article.scss";
@import "uikit/scss/core/comment.scss";
@import "uikit/scss/core/cover.scss";
// Navs
@import "uikit/scss/core/nav.scss";
@import "uikit/scss/core/navbar.scss";
@import "uikit/scss/core/subnav.scss";
@import "uikit/scss/core/breadcrumb.scss";
@import "uikit/scss/core/pagination.scss";
@import "uikit/scss/core/tab.scss";
@import "uikit/scss/core/thumbnav.scss";
// Elements
@import "uikit/scss/core/list.scss";
@import "uikit/scss/core/description-list.scss";
@import "uikit/scss/core/table.scss";
@import "uikit/scss/core/form.scss";
// Common
@import "uikit/scss/core/button.scss";
@import "uikit/scss/core/icon.scss";
@import "uikit/scss/core/close.scss";
@import "uikit/scss/core/badge.scss";
@import "uikit/scss/core/alert.scss";
@import "uikit/scss/core/thumbnail.scss";
@import "uikit/scss/core/overlay.scss";
@import "uikit/scss/core/column.scss";
@import "uikit/scss/core/animation.scss";
// JavaScript
@import "uikit/scss/core/dropdown.scss";
@import "uikit/scss/core/modal.scss";
@import "uikit/scss/core/offcanvas.scss";
@import "uikit/scss/core/switcher.scss";
// Need to be loaded last
@import "uikit/scss/core/text.scss";
@import "uikit/scss/core/utility.scss";
@import "uikit/scss/core/flex.scss";
@import "uikit/scss/core/contrast.scss";
@import "uikit/scss/core/print.scss";
-9
View File
@@ -1,9 +0,0 @@
@import "custom_uikit";
.foo{
border: solid;
}
.ph-footer{
background-color: $navbar-background;
// height: 200px;
}
+218
View File
@@ -0,0 +1,218 @@
import { Application } from "jsr:@oak/oak/application";
import { Router } from "jsr:@oak/oak/router";
import { GameService } from "./server/game-service.ts";
import { Game } from "./server/types.ts";
import staticFiles from "https://deno.land/x/static_files@1.1.6/mod.ts";
import vento from "https://deno.land/x/vento@v0.9.1/mod.ts";
import { LoginService } from "./server/login-service.ts";
const env = vento();
setInterval(() => env.cache.clear(), 1000);
const gameService = new GameService(await Deno.openKv());
const loginService = LoginService.officialLoginService();
const router = new Router();
router.get("/", async (ctx) => {
const template = await env.load("templates/home.vto");
const result = await template({ tab: "home" });
ctx.response.body = result.content;
});
router.get("/calendrier", async (ctx) => {
const template = await env.load("templates/calendrier.vto");
const result = await template({
tab: "calendrier",
});
ctx.response.body = result.content;
});
router.get("/nouvelles", async (ctx) => {
const template = await env.load("templates/nouvelles.vto");
const result = await template({ tab: "nouvelles" });
ctx.response.body = result.content;
});
router.get("/contact", async (ctx) => {
const template = await env.load("templates/contact.vto");
const result = await template({ tab: "contact" });
ctx.response.body = result.content;
});
router.get("/reglement", async (ctx) => {
const template = await env.load("templates/reglement.vto");
const result = await template({ tab: "reglement" });
ctx.response.body = result.content;
});
router.get("/login", async (ctx) => {
const username = ctx.request.url.searchParams.get("username") || "";
const password = ctx.request.url.searchParams.get("password") || "";
if (!(await loginService.validateCredentials(username, password))) {
ctx.response.status = 403;
return;
}
await loginService.login(ctx);
ctx.response.redirect("/membre/games-editor/today");
});
const memberRouter = new Router();
memberRouter.use(async (ctx, next) => {
const isLoggedIn = await loginService.isLoggedIn(ctx);
if (ctx.request.url.pathname !== "/membre" && !isLoggedIn) {
ctx.response.redirect("/membre");
return;
}
ctx.params.isLoggedIn = isLoggedIn;
await next();
});
memberRouter.get("/", async (ctx) => {
const template = await env.load("templates/membre.vto");
const result = await template({
tab: "membre",
isLoggedIn: ctx.params.isLoggedIn,
});
ctx.response.body = result.content;
});
function today(): Date {
const date = new Date().toLocaleDateString("fr-CA", {
timeZone: "America/New_York",
});
return new Date(date);
}
memberRouter.get("/games-editor/today", async (ctx) => {
const template = await env.load("templates/partials/games-editor.vto");
const games = await gameService.getAllGames();
const lastGameDay = games
.map((g) => g.date)
.filter((d) => new Date(d) <= today())
.sort()
.reverse()[0];
const result = await template({
tab: "membre",
selectedYear: null,
isToday: true,
games: games.filter((g) => g.date === lastGameDay),
years: [...new Set(games.map((x) => x.year))].sort().reverse(),
});
ctx.response.body = result.content;
});
memberRouter.get("/games-editor/:year", async (ctx) => {
const template = await env.load("templates/partials/games-editor.vto");
const games = await gameService.getAllGames();
const selectedYear = parseInt(ctx.params.year);
const result = await template({
tab: "membre",
selectedYear: selectedYear,
games: games.filter((g) => g.year === selectedYear),
years: [...new Set(games.map((x) => x.year))].sort().reverse(),
});
ctx.response.body = result.content;
});
memberRouter.get("/new-game-editor", async (ctx) => {
const template = await env.load("templates/partials/new-games-editor.vto");
const result = await template({
tab: "membre",
});
ctx.response.body = result.content;
});
memberRouter.post("/new-game", async (ctx) => {
const payload = await ctx.request.body.form();
const preGame = {
date: payload.get("game-date"),
time: payload.get("game-time"),
away: payload.get("away-team"),
home: payload.get("home-team"),
};
const [game, error] = await gameService.createNewGame(preGame);
if (error !== "") {
const template = await env.load("templates/partials/new-game-error.vto");
const result = await template({
tab: "membre",
error: error,
});
ctx.response.status = 500;
ctx.response.body = result.content;
return;
}
const template = await env.load("templates/partials/single-game-editor.vto");
const result = await template({
tab: "membre",
game: game,
});
ctx.response.headers.set("game-id", game?.id ?? "");
ctx.response.body = result.content;
});
memberRouter.delete("/games/:gameId", async (ctx) => {
if (!(await loginService.isLoggedIn(ctx))) {
ctx.response.redirect("/membre");
return;
}
const success = await gameService.deleteGameById(ctx.params.gameId);
ctx.response.body = `${success}`;
});
memberRouter.post("/games/:gameId", async (ctx) => {
if (!(await loginService.isLoggedIn(ctx))) {
ctx.response.redirect("/membre");
return;
}
const payload = await ctx.request.body.form();
let preGame = {
awayScore: payload.get("away-score") ?? null,
homeScore: payload.get("home-score") ?? null,
rain: payload.get("game-type") === "rain",
practice: payload.get("game-type") === "practice",
};
preGame = Object.fromEntries(
Object.entries(preGame).filter(([_, v]) => v !== null),
) as Partial<Game>;
const success = await gameService.updateGame(ctx.params.gameId, preGame);
ctx.response.body = success
? `<i class="fa fa-floppy-o" aria-hidden="true"></i>`
: `<i class="fa fa-exclamation-triangle" aria-hidden="true"></i>`;
});
const apiRouter = new Router();
apiRouter.get("/results/:year.json", async (ctx) => {
ctx.response.json = true;
const games = await gameService.getAllGames();
ctx.response.body = games
.filter((g) => g.year == ctx.params.year)
.map((g) => {
g[g.home] = parseInt(g.homeScore);
g[g.away] = parseInt(g.awayScore);
return g;
});
});
apiRouter.get("/available-years.json", async (ctx) => {
ctx.response.json = true;
const games = await gameService.getAllGames();
ctx.response.body = [...new Set(games.map((g) => g.year))];
});
router.use("/membre", memberRouter.routes());
router.use("/api", apiRouter.routes());
const app = new Application();
app.use(router.routes());
app.use(staticFiles("static", { brotli: true, fetch: true }));
await app.listen({ port: 8000 });
+323
View File
@@ -0,0 +1,323 @@
import { Game, PreGame } from "./types.ts";
import {
assertEquals,
assertNotEquals,
} from "https://deno.land/std@0.224.0/assert/mod.ts";
type GamePrimaryKey = ["phenix", "games", string];
type date = [number, number, number];
type time = [number, number];
type DateIndex = ["phenix", "indexes", "game-date", ...date, ...time];
export class GameService {
readonly kv: Deno.Kv;
private readonly DATE_VALIDATOR =
/^(?<year>\d{4})-(?<month>\d{1,2})-(?<day>\d{1,2})$/;
private readonly TIME_VALIDATOR = /^(?<hour>\d{1,2})(:|h)(?<minute>\d{1,2})$/;
private readonly VALID_TEAMS: string[] = [
"jaune",
"rouge",
"bleu",
"gris",
"vert",
"noir",
"orange",
"mauve",
];
constructor(kv: Deno.Kv) {
this.kv = kv;
}
private chronologicalGameOrder(game1: Game, game2: Game): number {
if (game1.date < game2.date) {
return 1;
}
if (game1.date > game2.date) {
return -1;
}
if (game1.time < game2.time) {
return 1;
}
if (game1.time > game2.time) {
return -1;
}
return 0;
}
async getAllGames(): Promise<Game[]> {
const ite = this.kv.list<Game>({ prefix: ["phenix", "games"] });
return (await Array.fromAsync(ite))
.map((e) => e.value)
.sort(this.chronologicalGameOrder);
}
private gamePrimaryKey(id: string): GamePrimaryKey {
return ["phenix", "games", id];
}
private dateIndex(date: string, time: string): DateIndex | null {
let destructedDate = this.DATE_VALIDATOR.exec(date)?.groups;
let destructedTime = this.TIME_VALIDATOR.exec(time)?.groups;
if (!destructedDate || !destructedTime) {
return null;
}
return [
"phenix",
"indexes",
"game-date",
parseInt(destructedDate.year),
parseInt(destructedDate.month),
parseInt(destructedDate.day),
parseInt(destructedTime.hour),
parseInt(destructedTime.minute),
];
}
private cleanTime(raw: string): string {
const groups = this.TIME_VALIDATOR.exec(raw)!.groups!;
return `${groups.hour.padStart(2, "0")}:${groups.minute.padStart(2, "0")}`;
}
private cleanDate(raw: string): string {
const groups = this.DATE_VALIDATOR.exec(raw)!.groups!;
return `${groups.year}-${groups.month.padStart(2, "0")}-${groups.day.padStart(2, "0")}`;
}
private extractYearFromDate(date: string): number {
return parseInt(this.DATE_VALIDATOR.exec(date)!.groups!.year);
}
private createGame(preGame: PreGame): Game {
const ret = {
...preGame,
id: crypto.randomUUID(),
practice: false,
rain: false,
year: this.extractYearFromDate(preGame.date),
homeScore: null,
awayScore: null,
};
ret.time = this.cleanTime(ret.time);
ret.date = this.cleanDate(ret.date);
return ret;
}
private validatePregate(preGame: PreGame): string {
if (!this.DATE_VALIDATOR.test(preGame.date)) {
return `Invalide date format ${preGame.date}`;
}
if (!this.TIME_VALIDATOR.test(preGame.time)) {
return `Invalide time format ${preGame.time}`;
}
if (!this.VALID_TEAMS.includes(preGame.away)) {
return `Invalide away format ${preGame.away}`;
}
if (!this.VALID_TEAMS.includes(preGame.home)) {
return `Invalide home format ${preGame.home}`;
}
if (preGame.home === preGame.away) {
return `Home and away teams must be different (received ${preGame.home} for both)`;
}
return "";
}
async createNewGame(preGame: PreGame): Promise<[Game | null, string]> {
if (this.validatePregate(preGame) !== "") {
return [null, this.validatePregate(preGame)];
}
const game = this.createGame(preGame);
const dateIndex = this.dateIndex(game.date, game.time);
if (!dateIndex) {
return [null, "Cound not parse date or time"];
}
const precondition = await this.kv.get<string>(dateIndex);
if (precondition.value !== null) {
return [null, "game already exists " + precondition.value];
}
const res = await this.kv
.atomic()
.check(precondition)
.set(this.gamePrimaryKey(game.id), game)
.set(dateIndex, game.id)
.commit();
if (!res.ok) {
return [null, "Transaction failed"];
}
return [game, ""];
}
async getGameById(id: string): Promise<Game | null> {
const res = await this.kv.get<Game>(this.gamePrimaryKey(id));
return res.value;
}
async deleteGameById(id: string): Promise<boolean> {
const precond = await this.kv.get<Game>(this.gamePrimaryKey(id));
if (precond.value === null) {
return false;
}
const res = await this.kv
.atomic()
.check(precond)
.delete(this.gamePrimaryKey(precond.value.id))
.delete(this.dateIndex(precond.value.date, precond.value.time)!)
.commit();
return res.ok;
}
async updateGame(id: string, partial: Partial<Game>): Promise<boolean> {
delete partial.id;
const precond = await this.kv.get<Game>(this.gamePrimaryKey(id));
if (precond.value === null) {
return false;
}
const res = await this.kv
.atomic()
.check(precond)
.delete(this.gamePrimaryKey(precond.value.id))
.delete(this.dateIndex(precond.value.date, precond.value.time)!)
.set(
this.dateIndex(precond.value.date, precond.value.time)!,
precond.value.id,
)
.set(this.gamePrimaryKey(precond.value.id), {
...precond.value,
...partial,
})
.commit();
return res.ok;
}
}
Deno.test("saving simple games", async (t) => {
const kv = await Deno.openKv();
const service = new GameService(kv);
async function deleteAllKeys() {
const keys = kv.list({ prefix: [] });
for await (const entry of keys) {
await kv.delete(entry.key);
}
}
function validePreGame(seed: number): PreGame {
let year = ((645 * seed + 162) % 10000) + 1;
let month = ((335 * seed + 71) % 12) + 1;
let day = ((72625 * seed + 176) % 28) + 1;
return {
date: `${(year + "").padStart(4, "0")}-${(month + "").padStart(2, "0")}-${(day + "").padStart(2, "0")}`,
time: "18:45",
away: "jaune",
home: "rouge",
};
}
await deleteAllKeys();
await t.step("creating games", async () => {
const preGame = validePreGame(7276);
const [game, error] = await service.createNewGame(preGame);
assertEquals(error, "");
const ret = await service.getGameById(game!.id);
assertEquals(game, ret);
});
await deleteAllKeys();
await t.step("creating games with old date format", async () => {
const preGame = validePreGame(7276);
preGame.date = "2017-8-5";
const [game, error] = await service.createNewGame(preGame);
assertEquals(error, "");
assertEquals(game?.date, "2017-08-05");
});
await deleteAllKeys();
await t.step("creating games with old time format", async () => {
const preGame = validePreGame(7276);
preGame.time = "9:00";
const [game, error] = await service.createNewGame(preGame);
assertEquals(error, "");
assertEquals(game?.time, "09:00");
});
await deleteAllKeys();
await t.step(
"saving two games in the same timeslot should fail",
async () => {
const preGame = validePreGame(7276);
let [_, error] = await service.createNewGame(preGame);
assertEquals(error, "");
[_, error] = await service.createNewGame(preGame);
assertNotEquals(error, "");
},
);
await deleteAllKeys();
await t.step("saving games with bad fields", async () => {
let i = 0;
for (const key of Object.keys(validePreGame(7276))) {
let [_, error] = await service.createNewGame({
...validePreGame(7262 + i),
[key]: `Broken ${key}`,
});
assertNotEquals(error, "");
i++;
}
});
await t.step("saving games with the same home and away teams", async () => {
const preGame = validePreGame(7276);
preGame.home = preGame.away;
let [_, error] = await service.createNewGame(preGame);
assertNotEquals(error, "");
});
await deleteAllKeys();
await t.step("listing games", async () => {
for (let i = 0; i < 10; i++) {
await service.createNewGame(validePreGame(666 + i));
}
assertEquals((await service.getAllGames()).length, 10);
});
await deleteAllKeys();
await t.step("deleting games", async () => {
let [game, error] = await service.createNewGame(validePreGame(8992));
await service.deleteGameById(game!.id);
assertEquals((await service.getAllGames()).length, 0);
[game, error] = await service.createNewGame(validePreGame(8992));
assertEquals(error, "");
});
await deleteAllKeys();
await t.step("updating game scores", async () => {
let [game, _] = await service.createNewGame(validePreGame(8992));
const ret = await service.updateGame(game!.id, {
homeScore: 10,
awayScore: 32,
});
assertEquals(ret, true);
game = await service.getGameById(game!.id);
assertEquals(game!.homeScore, 10);
assertEquals(game!.awayScore, 32);
});
await deleteAllKeys();
await kv.close();
});
+111
View File
@@ -0,0 +1,111 @@
import {
assert,
assertFalse,
} from "https://deno.land/std@0.224.0/assert/mod.ts";
type User = { username: string; passwordHashWithSalt: string };
const officialUsers: User[] = [
{
username: "marqueur",
passwordHashWithSalt:
"5603007580f73044864e7a0b66744f405406eaaf28fa514d724ccf11d010bd89:070b1a477e6a877d44f31961dc0402a9f3258465eed73ab6a9110c461ac68714",
},
];
export class LoginService {
private readonly users: User[];
private readonly sessionKey: string;
constructor(users: User[], sessionKey: string) {
this.users = users;
this.sessionKey = sessionKey;
}
public static officialLoginService(): LoginService {
return new LoginService(
officialUsers,
Deno.env.get("SESSION_KEY") || "dev-only",
);
}
private async hashMessage(message: string): Promise<string> {
const msgUint8 = new TextEncoder().encode(message); // encode as (utf-8) Uint8Array
const hashBuffer = await crypto.subtle.digest("SHA-256", msgUint8); // hash the message
const hashArray = Array.from(new Uint8Array(hashBuffer)); // convert buffer to byte array
const hashHex = hashArray
.map((b) => b.toString(16).padStart(2, "0"))
.join(""); // convert bytes to hex string
return hashHex;
}
private async shittyHmac(message: string, salt: string): Promise<string> {
const h1 = await this.hashMessage(message + salt);
const h2 = await this.hashMessage(salt + message);
return await this.hashMessage(h1 + h2);
}
async hashPassword(password: string): Promise<string> {
const salt = await this.hashMessage(`${Math.random()}`);
const hash = await this.shittyHmac(password, salt);
return `${salt}:${hash}`;
}
async verifyPassword(
password: string,
passwordHashWithSalt: string,
): Promise<boolean> {
const [passwordSalt, passwordHash] = passwordHashWithSalt.split(":");
return passwordHash === (await this.shittyHmac(password, passwordSalt));
}
async validateCredentials(
username: string,
password: string,
): Promise<boolean> {
for (const user of this.users) {
if (user.username === username) {
return this.verifyPassword(password, user.passwordHashWithSalt);
}
}
return false;
}
async login(ctx: any): Promise<void> {
const nDays = 90;
const maxAgesInSecond = nDays * 24 * 3600;
const maxUnixEpoch = Math.floor(Date.now() / 1000) + maxAgesInSecond;
await ctx.cookies.set("phenix-session", `${maxUnixEpoch}`, {
maxAge: maxAgesInSecond,
});
await ctx.cookies.set(
"phenix-session-sign",
await this.shittyHmac(`${maxUnixEpoch}`, this.sessionKey),
{
maxAge: maxAgesInSecond,
},
);
}
async isLoggedIn(ctx: any): Promise<boolean> {
const expiration = await ctx.cookies.get("phenix-session");
const signature = await ctx.cookies.get("phenix-session-sign");
if (signature !== (await this.shittyHmac(expiration, this.sessionKey))) {
return false;
}
if (!expiration || !/^\d+$/.test(expiration)) {
return false;
}
return Date.now() < parseInt(expiration) * 1000;
}
}
Deno.test("login service", async (t) => {
await t.step("hashing password", async () => {
const service = new LoginService([]);
const passwordHashWithSalt = await service.hashPassword("qwerty");
assert(await service.verifyPassword("qwerty", passwordHashWithSalt));
assertFalse(await service.verifyPassword("ytrewq", passwordHashWithSalt));
});
});
+19
View File
@@ -0,0 +1,19 @@
export type Game = {
id: string;
date: string;
time: string;
home: string;
away: string;
year: number;
homeScore: number | null;
awayScore: number | null;
practice: boolean;
rain: boolean;
};
export type PreGame = {
date: string;
time: string;
home: string;
away: string;
};
+8413
View File
File diff suppressed because it is too large. Load diff
+5
View File
@@ -0,0 +1,5 @@
[Dolphin]
SortRole=modificationtime
Timestamp=2018,3,19,17,32,48
Version=4
ViewMode=1
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
File renamed without changes.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
File renamed without changes.
Binary file not shown.
File renamed without changes.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
File renamed without changes.
+26
View File
@@ -0,0 +1,26 @@
import * as util from "./util.js";
import m from "https://esm.sh/mithril@2.2.2"
import _ from "https://esm.sh/lodash-es@4.17.21"
import {statsView, tabView, schedulView } from './schedule.js'
const calendarPage = {
view: function(){
const availableYears = util.getAvailableYears();
const year = _.get(m.route.param(), 'year', util.getDefaultYear());
return m('div.uk-grid.uk-margin-top.uk-margin-bottom',
m('div.uk-width-large-3-5.uk-width-medium-4-5.uk-width-small-1-1.uk-container-center',
[
m(statsView, {year}),
m(tabView, {year, availableYears}),
m(schedulView, {year}),
]),
)
}
}
m.route.mode = "hash";
m.route(document.getElementById('mithril-content'), "/", {
"/": calendarPage,
"/:year": calendarPage,
});
@@ -1,5 +1,6 @@
define(['m'], function(m) { import m from "https://esm.sh/mithril@2.2.2"
return function(size){
export function rainSvg (size){
return m("svg[viewBox='0 0 107.95 87.723']",{width: size, height: size}, [ return m("svg[viewBox='0 0 107.95 87.723']",{width: size, height: size}, [
m("defs[id='defs16']"), m("defs[id='defs16']"),
m("g[id='layer1'][transform='translate(-310.1 -167.39)']", [ m("g[id='layer1'][transform='translate(-310.1 -167.39)']", [
@@ -15,5 +16,4 @@ define(['m'], function(m) {
]) ])
]) ])
]); ]);
}; }
});
+2
View File
@@ -0,0 +1,2 @@
/*! jQuery v3.7.1 | (c) OpenJS Foundation and other contributors | jquery.org/license */
!function(e,t){"use strict";"object"==typeof module&&"object"==typeof module.exports?module.exports=e.document?t(e,!0):function(e){if(!e.document)throw new Error("jQuery requires a window with a document");return t(e)}:t(e)}("undefined"!=typeof window?window:this,function(ie,e){"use strict";var oe=[],r=Object.getPrototypeOf,ae=oe.slice,g=oe.flat?function(e){return oe.flat.call(e)}:function(e){return oe.concat.apply([],e)},s=oe.push,se=oe.indexOf,n={},i=n.toString,ue=n.hasOwnProperty,o=ue.toString,a=o.call(Object),le={},v=function(e){return"function"==typeof e&&"number"!=typeof e.nodeType&&"function"!=typeof e.item},y=function(e){return null!=e&&e===e.window},C=ie.document,u={type:!0,src:!0,nonce:!0,noModule:!0};function m(e,t,n){var r,i,o=(n=n||C).createElement("script");if(o.text=e,t)for(r in u)(i=t[r]||t.getAttribute&&t.getAttribute(r))&&o.setAttribute(r,i);n.head.appendChild(o).parentNode.removeChild(o)}function x(e){return null==e?e+"":"object"==typeof e||"function"==typeof e?n[i.call(e)]||"object":typeof e}var t="3.7.1",l=/HTML$/i,ce=function(e,t){return new ce.fn.init(e,t)};function c(e){var t=!!e&&"length"in e&&e.length,n=x(e);return!v(e)&&!y(e)&&("array"===n||0===t||"number"==typeof t&&0<t&&t-1 in e)}function fe(e,t){return e.nodeName&&e.nodeName.toLowerCase()===t.toLowerCase()}ce.fn=ce.prototype={jquery:t,constructor:ce,length:0,toArray:function(){return ae.call(this)},get:function(e){return null==e?ae.call(this):e<0?this[e+this.length]:this[e]},pushStack:function(e){var t=ce.merge(this.constructor(),e);return t.prevObject=this,t},each:function(e){return ce.each(this,e)},map:function(n){return this.pushStack(ce.map(this,function(e,t){return n.call(e,t,e)}))},slice:function(){return this.pushStack(ae.apply(this,arguments))},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},even:function(){return this.pushStack(ce.grep(this,function(e,t){return(t+1)%2}))},odd:function(){return this.pushStack(ce.grep(this,function(e,t){return t%2}))},eq:function(e){var t=this.length,n=+e+(e<0?t:0);return this.pushStack(0<=n&&n<t?[this[n]]:[])},end:function(){return this.prevObject||this.constructor()},push:s,sort:oe.sort,splice:oe.splice},ce.extend=ce.fn.extend=function(){var e,t,n,r,i,o,a=arguments[0]||{},s=1,u=arguments.length,l=!1;for("boolean"==typeof a&&(l=a,a=arguments[s]||{},s++),"object"==typeof a||v(a)||(a={}),s===u&&(a=this,s--);s<u;s++)if(null!=(e=arguments[s]))for(t in e)r=e[t],"__proto__"!==t&&a!==r&&(l&&r&&(ce.isPlainObject(r)||(i=Array.isArray(r)))?(n=a[t],o=i&&!Array.isArray(n)?[]:i||ce.isPlainObject(n)?n:{},i=!1,a[t]=ce.extend(l,o,r)):void 0!==r&&(a[t]=r));return a},ce.extend({expando:"jQuery"+(t+Math.random()).replace(/\D/g,""),isReady:!0,error:function(e){throw new Error(e)},noop:function(){},isPlainObject:function(e){var t,n;return!(!e||"[object Object]"!==i.call(e))&&(!(t=r(e))||"function"==typeof(n=ue.call(t,"constructor")&&t.constructor)&&o.call(n)===a)},isEmptyObject:function(e){var t;for(t in e)return!1;return!0},globalEval:function(e,t,n){m(e,{nonce:t&&t.nonce},n)},each:function(e,t){var n,r=0;if(c(e)){for(n=e.length;r<n;r++)if(!1===t.call(e[r],r,e[r]))break}else for(r in e)if(!1===t.call(e[r],r,e[r]))break;return e},text:function(e){var t,n="",r=0,i=e.nodeType;if(!i)while(t=e[r++])n+=ce.text(t);return 1===i||11===i?e.textContent:9===i?e.documentElement.textContent:3===i||4===i?e.nodeValue:n},makeArray:function(e,t){var n=t||[];return null!=e&&(c(Object(e))?ce.merge(n,"string"==typeof e?[e]:e):s.call(n,e)),n},inArray:function(e,t,n){return null==t?-1:se.call(t,e,n)},isXMLDoc:function(e){var t=e&&e.namespaceURI,n=e&&(e.ownerDocument||e).documentElement;return!l.test(t||n&&n.nodeName||"HTML")},merge:function(e,t){for(var n=+t.length,r=0,i=e.length;r<n;r++)e[i++]=t[r];return e.length=i,e},grep:function(e,t,n){for(var r=[],i=0,o=e.length,a=!n;i<o;i++)!t(e[i],i)!==a&&r.push(e[i]);return r},map:function(e,t,n){var r,i,o=0,a=[];if(c(e))for(r=e.length;o<r;o++)null!=(i=t(e[o],o,n))&&a.push(i);else for(o in e)null!=(i=t(e[o],o,n))&&a.push(i);return g(a)},guid:1,support:le}),"function"==typeof Symbol&&(ce.fn[Symbol.iterator]=oe[Symbol.iterator]),ce.each("Boolean Number String Function Array Date RegExp Object Error Symbol".split(" "),function(e,t){n["[object "+t+"]"]=t.toLowerCase()});var pe=oe.pop,de=oe.sort,he=oe.splice,ge="[\\x20\\t\\r\\n\\f]",ve=new RegExp("^"+ge+"+|((?:^|[^\\\\])(?:\\\\.)*)"+ge+"+$","g");ce.contains=function(e,t){var n=t&&t.parentNode;return e===n||!(!n||1!==n.nodeType||!(e.contains?e.contains(n):e.compareDocumentPosition&&16&e.compareDocumentPosition(n)))};var f=/([\0-\x1f\x7f]|^-?\d)|^-$|[^\x80-\uFFFF\w-]/g;function p(e,t){return t?"\0"===e?"\ufffd":e.slice(0,-1)+"\\"+e.charCodeAt(e.length-1).toString(16)+" ":"\\"+e}ce.escapeSelector=function(e){return(e+"").replace(f,p)};var ye=C,me=s;!function(){var e,b,w,o,a,T,r,C,d,i,k=me,S=ce.expando,E=0,n=0,s=W(),c=W(),u=W(),h=W(),l=function(e,t){return e===t&&(a=!0),0},f="checked|selected|async|autofocus|autoplay|conLine truncated
+99
View File
@@ -0,0 +1,99 @@
// alert("ok")
import * as util from "./util.js";
import * as resultParser from './resultParser.js'
import * as teams from './teams.js'
import m from "https://esm.sh/mithril@2.2.2"
import {rainSvg} from "./images.js";
import _ from "https://esm.sh/lodash-es@4.17.21"
import {statsView, tabView, scheduleTeamTags } from './schedule.js'
const nextGameDaySchedule = {};
nextGameDaySchedule._toDay = function(){
var now = new Date();
return new Date(now.getFullYear(), now.getMonth(), now.getDate());
};
nextGameDaySchedule.oninit = async function(){
const result = await m.request({
method: "GET",
url: `/api/results/2024.json`
});
const nightGames = resultParser.getNightGames(result);
nextGameDaySchedule.games = nextGameDaySchedule._getNextNightGame(nightGames, nextGameDaySchedule._toDay());
};
nextGameDaySchedule._getNextNightGame = function(games, date){
return _(games)
.filter(g => g.jsDate.getTime() >= date.getTime())
.last()
.games
.sort((g1, g2) => g1.jsDate - g2.jsDate);
};
nextGameDaySchedule._getTableHead = function(){
return m('thead', m('tr', [
m('td', 'Date'),
m('td', 'Heure'),
m('td', 'Receveur'),
m('td', 'Visiteur')
]));
};
nextGameDaySchedule._responsoveText = function(largeText, smallText, game){
var ret = [];
if(game.rain){
ret.push(rainSvg('1.5em'));
ret.push(' ');
} else if(game.practice){
ret.push(m('span.uk-badge.uk-badge-success', 'pratique!'));
ret.push(' ');
}
ret.push(m('span.uk-visible-large', largeText));
ret.push(m('span.uk-hidden-large', smallText));
return ret;
};
nextGameDaySchedule._getGamesRow = function(game){
return m('tr', [
m('td', nextGameDaySchedule._responsoveText(util.formatDate(game.jsDate),
util.formatDateSmall(game.jsDate),
game)),
m('td', game.time),
m('td', scheduleTeamTags.getHomeTeamTag(game)),
m('td',scheduleTeamTags.getAwayTeamTag(game))
]);
};
nextGameDaySchedule._getGamesRows = function(games){
return _.map(games, nextGameDaySchedule._getGamesRow);
};
nextGameDaySchedule.view = function(){
return m('table.uk-table.uk-table-hover.uk-table-striped.uk-table-condensed',[
nextGameDaySchedule._getTableHead(),
m('tbody',
nextGameDaySchedule._getGamesRows(nextGameDaySchedule.games)
)]);
};
const LittleCalendar = {}
LittleCalendar.view = function(){
return m(nextGameDaySchedule);
}
const containerIds = ['large-mithril-container',
'medium-mithril-container',
'small-mithril-container']
for(const id of containerIds){
m.mount(document.getElementById(id), LittleCalendar);
}
+136
View File
@@ -0,0 +1,136 @@
import * as _ from "https://esm.sh/lodash-es@4.17.21"
let resultParser = {};
resultParser._addJSDateToResult = function(res){
let date = res.date.split('-');
let time = _.isString(res.time) ? res.time.split(':'): [0, 0];
res.jsDate = new Date(
Number(date[0]),
Number(date[1]) - 1,
Number(date[2]),
Number(time[0]),
Number(time[1])
);
return res;
};
resultParser._setCanonicalPoints = function(res){
if(!_.isNumber(res.home_points) && _.isNumber(_.get(res, res.home))){
res.home_points = res[res.home];
}
if(!_.isNumber(res.away_points) && _.isNumber(_.get(res, res.away))){
res.away_points = res[res.away];
}
return res;
}
resultParser.parseResults = function(rawResults){
rawResults = _.map(rawResults, resultParser._setCanonicalPoints);
rawResults = _.map(rawResults, resultParser._addJSDateToResult);
rawResults = _.map(rawResults, resultParser._addCustomStyle);
return rawResults;
};
resultParser.getNightGames = function(rawResults){
let ret = {};
_.each(resultParser.parseResults(rawResults), function(res){
if(_.has(ret, res.date)){
ret[res.date].push(res);
}else{
ret[res.date] = [res];
}
});
return _.map(ret, function(games, date){
return resultParser._addJSDateToResult({date: date, games: games});
});
};
resultParser._getAllTeams = function(rawResults){
let homeTeams = _.map(rawResults, 'home');
let awayTeams = _.map(rawResults, 'away');
return _.uniq(_.concat(homeTeams, awayTeams));
};
resultParser._getWinner = function(res){
if(res.home_points > res.away_points){
return res.home;
}
if(res.home_points < res.away_points){
return res.away;
}
};
resultParser._hasWon = function(res, team){
return resultParser._getWinner(res) == team;
};
resultParser._hasLost = function(res, team){
return !resultParser._isDraw(res) && resultParser._getWinner(res) != team;
};
resultParser._isDraw = function(res){
return res.home_points == res.away_points;
};
resultParser._getPointsFor = function(res, team){
if(res.home == team){
return res.home_points;
}
return res.away_points;
};
resultParser._getPointsForOpponent = function(res, team){
if(res.home == team){
return res.away_points;
}
return res.home_points;
};
resultParser._getPointsForGame = function(res, team){
if(resultParser._hasWon(res, team)){
return 2;
}
return resultParser._isDraw(res) ? 1: 0;
};
resultParser._getTeamStats = function(rawResults, team){
let ret = {
team: team, gamePlayed: 0, victories: 0, points: 0,
defeats: 0, draws: 0, pointsFor: 0, pointsAgaint: 0};
_.each(rawResults, function(res){
if((team != res.home && team != res.away) || !_.isNumber(res.home_points)){
return;
}
ret.gamePlayed += 1;
ret.victories += resultParser._hasWon(res, team) ? 1: 0;
ret.defeats += resultParser._hasLost(res, team) ? 1: 0;
ret.draws += resultParser._isDraw(res) ? 1: 0;
ret.pointsFor += resultParser._getPointsFor(res, team);
ret.pointsAgaint += resultParser._getPointsForOpponent(res, team);
ret.points += resultParser._getPointsForGame(res, team);
});
return ret;
};
resultParser._removeTemporaryResults = function(rawResults){
return _.filter(rawResults, function(rawResult){
return !rawResult.temporary;
});
};
resultParser._isValidGame = function(game){
return !game.rain && ! game.practice;
};
resultParser.getStats = function(rawResults){
rawResults = _.filter(rawResults, resultParser._isValidGame);
rawResults = _.map(rawResults, resultParser._setCanonicalPoints);
let allTeams = resultParser._getAllTeams(resultParser._removeTemporaryResults(rawResults));
let getTeamStats = _.partial(resultParser._getTeamStats, rawResults);
return _.map(allTeams, getTeamStats);
};
export const getStats = resultParser.getStats;
export const getNightGames = resultParser.getNightGames;
+218
View File
@@ -0,0 +1,218 @@
import * as util from "./util.js";
import * as resultParser from './resultParser.js'
import * as teams from './teams.js'
import m from "https://esm.sh/mithril@2.2.2"
import {rainSvg} from "./images.js";
import _ from "https://esm.sh/lodash-es@4.17.21"
function ppYear(year, availableYears) {
return _.last(availableYears) === year ? "" : year;
}
export const scheduleTeamTags = {};
scheduleTeamTags._getTeamTag = function(teamName){
var teamColor = teams.getTeamColor(teamName);
return [
m('i.fa.fa-flag', {style: {color: teamColor}}),
m('span', ' ' + teamName)
];
};
scheduleTeamTags._getAwayPracticeTeamTag = function(){
return [
m('i.fa.fa-hand-spock-o', {style: {color: ' #ff1493'}, title: 'pratique'}),
m('span', ' Amis #1')
];
};
scheduleTeamTags._getHomePracticeTeamTag = function(){
return [
m('i.fa.fa-hand-spock-o', {style: {color: '#acbf60'}, title: 'pratique'}),
m('span', ' Amis #2')
];
};
scheduleTeamTags.getAwayTeamTag = function(game){
if(game.practice){
return scheduleTeamTags._getAwayPracticeTeamTag();
}
return scheduleTeamTags._getTeamTag(game.away);
};
scheduleTeamTags.getHomeTeamTag = function(game){
if(game.practice){
return scheduleTeamTags._getHomePracticeTeamTag();
}
return scheduleTeamTags._getTeamTag(game.home);
};
export const statsView = {};
statsView.stats = [];
statsView.oninit = async function(vnode){
if(statsView.currentYear === vnode.attrs.year){
return;
}
statsView.currentYear = vnode.attrs.year;
const result = await m.request({
method: "GET",
url: `/api/results/${vnode.attrs.year}.json`
});
statsView.stats = resultParser.getStats(result)
return result;
};
statsView.onupdate = statsView.oninit;
statsView.getStatRow = function(teamStats){
var formatStat = function(n){
return teamStats.gamePlayed === 0 ? '-' : n;
};
return m('tr', [
m('td', teamStats.team),
m('td', teamStats.gamePlayed),
m('td', formatStat(teamStats.victories)),
m('td', formatStat(teamStats.defeats)),
m('td', formatStat(teamStats.draws)),
m('td', formatStat(teamStats.pointsFor)),
m('td', formatStat(teamStats.pointsAgaint)),
m('td', formatStat(teamStats.pointsFor - teamStats.pointsAgaint)),
m('td', formatStat(teamStats.points))
]);
};
statsView.isStatForValidTeam = function(stat){
var teamNames = _.map(teams.teams(), 'name');
return _.includes(teamNames, stat.team);
}
statsView.mainTable = function(stats){
var orderedStats = _.reverse(_.sortBy(stats, ['points', 'pointsFor']));
return m('table.uk-table.uk-table-hover.uk-table-striped',[
m('thead', m('tr', [
m('th', 'Équipes'),
m('th', 'PJ'),
m('th', 'V'),
m('th', 'D'),
m('th', 'N'),
m('th', 'PP'),
m('th', 'PC'),
m('th', 'DIF'),
m('th', 'PTS')
])),
m('tbody', _(orderedStats)
.filter(statsView.isStatForValidTeam)
.map(statsView.getStatRow)
.value())
]);
};
statsView.legend = function(){
var items = ["PJ : Parties joués", "V : Victoire", "D : Défaite",
"N : Nul", "PP : Points pour", "PC : Points contre",
"DIF : Diférenciel","PTS : Points"];
return m('ul.uk-subnav.uk-subnav-line.uk-flex-center',[
_.map(items, function(itm){
return m('li', itm);
})
]);
};
statsView.view = function(vnode){
return m('div.uk-grid',
m('div.uk-width-medium-1-1.uk-width-large-1-1.uk-container-center',[
m('h2', 'Classement ' + vnode.attrs.year),
statsView.mainTable(statsView.stats),
statsView.legend()
]));
};
export const schedulView = {};
schedulView.oninit = async function(vnode){
if(vnode.attrs.year === schedulView.currentYear){
return;
}
schedulView.currentYear = vnode.attrs.year;
const result = await m.request({
method: "GET",
url: `/api/results/${vnode.attrs.year}.json`
});
schedulView.games = resultParser.getNightGames(result)
};
schedulView.onupdate = schedulView.oninit;
schedulView._asGamePoints = function(points){
return !_.isNumber(points) ? '-' : points + '';
};
schedulView._rainIcon = function(game){
if(game.rain){
return m('span', {title: 'pluie, partie annulée.'}, rainSvg('1.5em'));
}
return m('span', {style: {visibility: 'hidden'}}, rainSvg('1.5em'));
};
schedulView._gameName = function(game){
return [schedulView._rainIcon(game),
" ",
game.time];
};
schedulView._gameRow = function(game){
return m('tr',[
m('td', schedulView._gameName(game)),
m('td', scheduleTeamTags.getAwayTeamTag(game)),
m('td', schedulView._asGamePoints(game.away_points)),
m('td', 'vs'),
m('td', scheduleTeamTags.getHomeTeamTag(game)),
m('td', schedulView._asGamePoints(game.home_points))
]);
};
schedulView._gameView = function(gameNight){
return m('div', [m('h3', util.formatDate(gameNight.jsDate)),
m('table.uk-table.uk-table-hover.uk-table-condensed.uk-table-striped',
m('tbody',[
_.map(gameNight.games, schedulView._gameRow),
])
)
]);
};
schedulView.view = function(){
return m('div.uk-grid',
m('div.uk-width-large-3-5.uk-width-medium-1-1',
_.map(schedulView.games, schedulView._gameView)));
};
export const tabView = {};
tabView._createTab = function(activeYear, availableYears, year){
const isActive = (activeYear == year) || (activeYear == ppYear(year, availableYears));
return m('li', {'class': isActive ? 'uk-active': ''}, // 'uk-active'
m('a', {href: '#/' + ppYear(year, availableYears)}, 'Saison ' + year));
}
tabView.view = function(vnode){
const activeYear = vnode.attrs.year;
const availableYears = vnode.attrs.availableYears;
const createTab = _.partial(tabView._createTab, activeYear, availableYears);
return m('div.uk-margin', m('h2', 'Calendrier ' + ppYear(activeYear, availableYears)),
m('ul.uk-tab', _.reverse(_.map(availableYears, createTab))));
};
+20
View File
@@ -0,0 +1,20 @@
import * as _ from "https://esm.sh/lodash-es@4.17.21"
export function teams(){
return [
{name: 'remplaçants', color: '#FFA500'},
{name: 'jaune', color: '#FF0'},
{name:'rouge', color: '#F00'},
{name:'bleu', color: '#00F'},
{name:'gris', color: '#808080'},
{name:'vert', color: '#008000'},
{name: 'noir', color: '#000000'},
{name: 'orange', color: '#FFA500'},
{name: 'mauve', color: '#E0B0FF'}
];
};
export function getTeamColor(teamName){
return teams().filter(t => t.name == teamName)[0]?.color;
};
+3
View File
@@ -0,0 +1,3 @@
/*! UIkit 2.27.2 | http://www.getuikit.com | (c) 2014 YOOtheme | MIT License */
!function(t){if("function"==typeof define&&define.amd&&define("uikit",function(){var i=window.UIkit||t(window,window.jQuery,window.document);return i.load=function(t,e,n,o){var s,a=t.split(","),r=[],l=(o.config&&o.config.uikit&&o.config.uikit.base?o.config.uikit.base:"").replace(/\/+$/g,"");if(!l)throw new Error("Please define base path to UIkit in the requirejs config.");for(s=0;s<a.length;s+=1){var c=a[s].replace(/\./g,"/");r.push(l+"/components/"+c)}e(r,function(){n(i)})},i}),!window.jQuery)throw new Error("UIkit requires jQuery");window&&window.jQuery&&t(window,window.jQuery,window.document)}(function(t,i,e){"use strict";var n={},o=t.UIkit?Object.create(t.UIkit):void 0;if(n.version="2.27.2",n.noConflict=function(){return o&&(t.UIkit=o,i.UIkit=o,i.fn.uk=o.fn),n},n.prefix=function(t){return t},n.$=i,n.$doc=n.$(document),n.$win=n.$(window),n.$html=n.$("html"),n.support={},n.support.transition=function(){var t=function(){var t,i=e.body||e.documentElement,n={WebkitTransition:"webkitTransitionEnd",MozTransition:"transitionend",OTransition:"oTransitionEnd otransitionend",transition:"transitionend"};for(t in n)if(void 0!==i.style[t])return n[t]}();return t&&{end:t}}(),n.support.animation=function(){var t=function(){var t,i=e.body||e.documentElement,n={WebkitAnimation:"webkitAnimationEnd",MozAnimation:"animationend",OAnimation:"oAnimationEnd oanimationend",animation:"animationend"};for(t in n)if(void 0!==i.style[t])return n[t]}();return t&&{end:t}}(),function(){Date.now=Date.now||function(){return(new Date).getTime()};for(var t=["webkit","moz"],i=0;i<t.length&&!window.requestAnimationFrame;++i){var e=t[i];window.requestAnimationFrame=window[e+"RequestAnimationFrame"],window.cancelAnimationFrame=window[e+"CancelAnimationFrame"]||window[e+"CancelRequestAnimationFrame"]}if(/iP(ad|hone|od).*OS 6/.test(window.navigator.userAgent)||!window.requestAnimationFrame||!window.cancelAnimationFrame){var n=0;window.requestAnimationFrame=function(t){var i=Date.now(),e=Math.max(n+16,i);return setTimeout(function(){t(n=e)},e-i)},window.cancelAnimationFrame=clearTimeout}}(),n.support.touch="ontouchstart"in document||t.DocumentTouch&&document instanceof t.DocumentTouch||t.navigator.msPointerEnabled&&t.navigator.msMaxTouchPoints>0||t.navigator.pointerEnabled&&t.navigator.maxTouchPoints>0||!1,n.support.mutationobserver=t.MutationObserver||t.WebKitMutationObserver||null,n.Utils={},n.Utils.isFullscreen=function(){return document.webkitFullscreenElement||document.mozFullScreenElement||document.msFullscreenElement||document.fullscreenElement||!1},n.Utils.str2json=function(t,i){try{return i?JSON.parse(t.replace(/([\$\w]+)\s*:/g,function(t,i){return'"'+i+'":'}).replace(/'([^']+)'/g,function(t,i){return'"'+i+'"'})):new Function("","var json = "+t+"; return JSON.parse(JSON.stringify(json));")()}catch(e){return!1}},n.Utils.debounce=function(t,i,e){var n;return function(){var o=this,s=arguments,a=function(){n=null,e||t.apply(o,s)},r=e&&!n;clearTimeout(n),n=setTimeout(a,i),r&&t.apply(o,s)}},n.Utils.throttle=function(t,i){var e=!1;return function(){e||(t.call(),e=!0,setTimeout(function(){e=!1},i))}},n.Utils.removeCssRules=function(t){var i,e,n,o,s,a,r,l,c,u;t&&setTimeout(function(){try{for(u=document.styleSheets,o=0,r=u.length;r>o;o++){for(n=u[o],e=[],n.cssRules=n.cssRules,i=s=0,l=n.cssRules.length;l>s;i=++s)n.cssRules[i].type===CSSRule.STYLE_RULE&&t.test(n.cssRules[i].selectorText)&&e.unshift(i);for(a=0,c=e.length;c>a;a++)n.deleteRule(e[a])}}catch(d){}},0)},n.Utils.isInView=function(t,e){var o=i(t);if(!o.is(":visible"))return!1;var s=n.$win.scrollLeft(),a=n.$win.scrollTop(),r=o.offset(),l=r.left,c=r.top;return e=i.extend({topoffset:0,leftoffset:0},e),c+o.height()>=a&&c-e.topoffset<=a+n.$win.height()&&l+o.width()>=s&&l-e.leftoffset<=s+n.$win.width()?!0:!1},n.Utils.checkDisplay=function(t,e){var o=n.$("[data-uk-margin], [data-uk-grid-match], [data-uk-grid-margin], [data-uk-check-display]",t||document);return t&&!o.length&&(o=i(t)),o.trigger("display.uk.check"),e&&("string"!=typeof e&&(e='[class*="uk-animation-"]'),o.find(e).each(function(){var t=n.$(this),i=t.attr("class"),e=i.match(/uk-animation-(.+)/);t.removeClass(e[0]).width(),t.addClass(e[0])})),o},n.Utils.options=function(t){if("string"!=i.type(t))return t;-1!=t.indexOf(":")&&"}"!=t.trim().substr(-1)&&(t="{"+t+"}");var e=t?t.indexOf("{"):-1,o={};if(-1!=e)try{o=n.Utils.str2json(t.substr(e))}catch(s){}return o},n.Utils.animate=function(t,e){var o=i.Deferred();return t=n.$(t),t.css("display","none").addClass(e).one(n.support.animation.end,function(){t.removeClass(e),o.resolve()}),t.css("display",""),o.promise()},n.Utils.uid=function(t){return(t||"id")+(new Date).getTime()+"RAND"+Math.ceil(1e5*Math.random())},n.Utils.template=function(t,i){for(var e,n,o,s,a=t.replace(/\n/g,"\\n").replace(/\{\{\{\s*(.+?)\s*\}\}\}/g,"{{!$1}}").split(/(\{\{\s*(.+?)\s*\}\})/g),r=0,l=[],c=0;r<a.length;){if(e=a[r],e.match(/\{\{\s*(.+?)\s*\}\}/))switch(r+=1,e=a[r],n=e[0],o=e.substring(e.match(/^(\^|\#|\!|\~|\:)/)?1:0Line truncated
if(e=u.split("-"),h=d[u]?d[u]:d["bottom-left"],this.justified&&this.justified.length)i(a.css({left:0}),this.justified,c);else if(this.options.preventflip!==!0){var p;switch(this.checkBoundary(n.left+h.left,n.top+h.top,r,l,c)){case"x":"x"!==this.options.preventflip&&(p=o.x[u]||"right-top");break;case"y":"y"!==this.options.preventflip&&(p=o.y[u]||"top-left");break;case"xy":this.options.preventflip||(p=o.xy[u]||"right-bottom")}p&&(e=p.split("-"),h=d[p]?d[p]:d["bottom-left"],a.addClass("uk-dropdown-autoflip"),this.checkBoundary(n.left+h.left,n.top+h.top,r,l,c)&&(e=u.split("-"),h=d[u]?d[u]:d["bottom-left"]))}r>c&&(a.addClass("uk-dropdown-stack"),this.trigger("stack.uk.dropdown",[this])),a.css(h).css("display","").addClass("uk-dropdown-"+e[0])}},checkBoundary:function(i,e,n,o,s){var a="";return(0>i||i-t.$win.scrollLeft()+n>s)&&(a+="x"),(e-t.$win.scrollTop()<0||e-t.$win.scrollTop()+o>window.innerHeight)&&(a+="y"),a}}),t.component("dropdownOverlay",{defaults:{justify:!1,cls:"",duration:200},boot:function(){t.ready(function(i){t.$("[data-uk-dropdown-overlay]",i).each(function(){var i=t.$(this);i.data("dropdownOverlay")||t.dropdownOverlay(i,t.Utils.options(i.attr("data-uk-dropdown-overlay")))})})},init:function(){var e=this;this.justified=this.options.justify?t.$(this.options.justify):!1,this.overlay=this.element.find("uk-dropdown-overlay"),this.overlay.length||(this.overlay=t.$('<div class="uk-dropdown-overlay"></div>').appendTo(this.element)),this.overlay.addClass(this.options.cls),this.on({"beforeshow.uk.dropdown":function(t,n){e.dropdown=n,e.justified&&e.justified.length&&i(e.overlay.css({display:"block",marginLeft:"",marginRight:""}),e.justified,e.justified.outerWidth())},"show.uk.dropdown":function(){var i=e.dropdown.dropdown.outerHeight(!0);e.dropdown.element.removeClass("uk-open"),e.overlay.stop().css("display","block").animate({height:i},e.options.duration,function(){e.dropdown.dropdown.css("visibility",""),e.dropdown.element.addClass("uk-open"),t.Utils.checkDisplay(e.dropdown.dropdown,!0)}),e.pointerleave=!1},"hide.uk.dropdown":function(){e.overlay.stop().animate({height:0},e.options.duration)},"pointerenter.uk.dropdown":function(){clearTimeout(e.remainIdle)},"pointerleave.uk.dropdown":function(){e.pointerleave=!0}}),this.overlay.on({mouseenter:function(){e.remainIdle&&(clearTimeout(e.dropdown.remainIdle),clearTimeout(e.remainIdle))},mouseleave:function(){e.pointerleave&&n&&(e.remainIdle=setTimeout(function(){n&&n.hide()},n.options.remaintime))}})}})}(UIkit),function(t){"use strict";var i=[];t.component("gridMatchHeight",{defaults:{target:!1,row:!0,ignorestacked:!1,observe:!1},boot:function(){t.ready(function(i){t.$("[data-uk-grid-match]",i).each(function(){var i,e=t.$(this);e.data("gridMatchHeight")||(i=t.gridMatchHeight(e,t.Utils.options(e.attr("data-uk-grid-match"))))})})},init:function(){var e=this;this.columns=this.element.children(),this.elements=this.options.target?this.find(this.options.target):this.columns,this.columns.length&&(t.$win.on("load resize orientationchange",function(){var i=function(){e.element.is(":visible")&&e.match()};return t.$(function(){i()}),t.Utils.debounce(i,50)}()),this.options.observe&&t.domObserve(this.element,function(){e.element.is(":visible")&&e.match()}),this.on("display.uk.check",function(){this.element.is(":visible")&&this.match()}.bind(this)),i.push(this))},match:function(){var i=this.columns.filter(":visible:first");if(i.length){var e=Math.ceil(100*parseFloat(i.css("width"))/parseFloat(i.parent().css("width")))>=100;return e&&!this.options.ignorestacked?this.revert():t.Utils.matchHeights(this.elements,this.options),this}},revert:function(){return this.elements.css("min-height",""),this}}),t.component("gridMargin",{defaults:{cls:"uk-grid-margin",rowfirst:"uk-row-first"},boot:function(){t.ready(function(i){t.$("[data-uk-grid-margin]",i).each(function(){var i,e=t.$(this);e.data("gridMargin")||(i=t.gridMargin(e,t.Utils.options(e.attr("data-uk-grid-margin"))))})})},init:function(){t.stackMargin(this.element,this.options)}})}(UIkit),function(t){"use strict";function i(i,e){return e?("object"==typeof i?(i=i instanceof jQuery?i:t.$(i),i.parent().length&&(e.persist=i,e.persist.data("modalPersistParent",i.parent()))):i="string"==typeof i||"number"==typeof i?t.$("<div></div>").html(i):t.$("<div></div>").html("UIkit.modal Error: Unsupported data type: "+typeof i),i.appendTo(e.element.find(".uk-modal-dialog")),e):void 0}var e,n=!1,o=0,s=t.$html;t.$win.on("resize orientationchange",t.Utils.debounce(function(){t.$(".uk-modal.uk-open").each(function(){return t.$(this).data("modal")&&t.$(this).data("modal").resize()})},150)),t.component("modal",{defaults:{keyboard:!0,bgclose:!0,minScrollHeight:150,center:!1,modal:!0},scrollable:!1,transition:!1,hasTransitioned:!0,init:function(){if(e||(e=t.$("body")),this.element.length){var i=this;this.paddingdir="padding-"+("left"==t.langdirection?"right":"left"),this.dialog=this.find(".uk-modal-dialog"),this.active=!1,this.element.attr("aria-hiddLine truncated
+63
View File
@@ -0,0 +1,63 @@
import m from "https://esm.sh/mithril@2.2.2"
import * as _ from "https://esm.sh/lodash-es@4.17.21"
let availableYears = []
m.request({
method: "GET",
url: `api/available-years.json`
}).then(d => {
availableYears = d.sort();
})
function resultatsURL (year){
var cacheBuster = window.Date.now();
year = !!year ? year: util.getDefaultYear();
return "api/resultats" + year + ".json?_=" + cacheBuster;
};
export function getAvailableYears(){
if(window.availableYears){
return _.clone(window.availableYears)
}
return availableYears.map(x => x)
};
export function getDefaultYear(){
return _.max(getAvailableYears());
}
export function formatDate(date){
const monthNames = ['janvier', 'février', 'mars', 'avril', 'mai', 'juin',
'juillet', 'août', 'septembre', 'octobre', 'novembre',
'decembre'];
return [date.getDate(),
monthNames[date.getMonth()],
date.getFullYear()].join(' ');
};
export function getResults(year){
var url = resultatsURL(year);
return m.request({method: "GET", url: url})
};
export function getDefaultResults() {
return getResults(getDefaultYear());
};
export function formatDateSmall(date){
var smallMonthNames = ['janv', 'févr', 'mars', 'avr', 'mai', 'juin',
'juill', 'août', 'sept', 'oct', 'nov',
'dec'];
return [date.getDate(),
smallMonthNames[date.getMonth()],
date.getFullYear() % 1000].join(' ');
}
+8
View File
@@ -0,0 +1,8 @@
{{ layout "templates/container.vto" }}
<div id="mithril-content"></div>
<script type=module src="scripts/calendar.js"></script>
{{ /layout }}
+35
View File
@@ -0,0 +1,35 @@
{{ layout "templates/container.vto" }}
<div class="uk-width-large-2-5 uk-width-medium-4-5 uk-width-small-1-1 uk-container-center">
<div class="uk-grid uk-margin">
<div class="uk-width-1-1">
<div style="height: 300px; width: 300px; background-size: 300px; background-image: url(images/logosansfond.JPG);" class="uk-cover-background uk-container-center"></div>
</div>
</div>
<div class="div uk-panel uk-panel-box uk-panel-box-secondary uk-container-center uk-margin">
<table class="uk-table">
<tr>
<td class="uk-text-right"><i class="fa fa-desktop"></i></td>
<td><a href="mailto:sportsphenixmtl@gmail.com">sportsphenixmtl@gmail.com</a></td>
</tr>
<tr>
<td class="uk-text-right"><i class="fa fa-phone"></i></td>
<td> (514) 838-8950</td>
</tr>
<tr>
<td class="uk-text-right"><i class="fa fa-envelope"></i></td>
<td>
<p> 10454 Sylvain-Garneau<br>Montréal, Québec H1C 0A2</p>
</td>
</tr>
<tr>
<td class="uk-text-right"><i class="fa fa-gitlab"></i></td>
<td>
<p> Le site web est ouvert et accessible sur <a href="https://gitlab.com/ballephenix/website">gitlab.</a></p>
</td>
</tr>
</table>
</div>
</div>
{{ /layout }}
+102
View File
@@ -0,0 +1,102 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Balle Phenix</title>
<link rel="shortcut icon" href="https://www.ballephenix.com/favicon.ico">
<meta name="viewport" content="width=device-width, initial-scale=1">
<script src="scripts/jquery-3.7.1.min.js"></script>
<script src="scripts/uikit.min.js"></script>
<meta name="viewport" content="width=device-width, initial-scale=1">
<script src="https://unpkg.com/htmx.org@2.0.0"></script>
<link rel="stylesheet" href="/css/style.css">
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/font-awesome/4.7.0/css/font-awesome.min.css">
</head>
<body>
<nav class="uk-navbar uk-navbar-attached">
<ul class="uk-navbar-nav uk-visible-large uk-navbar-content uk-navbar-center">
<li class="uk-parent">
<div class="uk-navbar-brand"><a href="https://www.facebook.com/SportsPhenixMtl"><i class="fa fa-facebook-square"></i></a></div>
</li>
<li class="{{ if it.tab === 'home'}}uk-active{{ /if }}">
<a href="/">
<div><i class="fa fa-home"></i> Accueil</div>
</a>
</li>
<li class="{{ if it.tab === 'nouvelles'}}uk-active{{ /if }}">
<a href="/nouvelles">
<div><i class="fa fa-newspaper-o"></i> Nouvelles</div>
</a>
</li>
<li class="{{ if it.tab === 'calendrier'}}uk-active{{ /if }}">
<a href="/calendrier">
<div><i class="fa fa-calendar"></i> Calendrier</div>
</a>
</li>
<li class="{{ if it.tab === 'reglement'}}uk-active{{ /if }}">
<a href="/reglement">
<div><i class="fa fa-legal"></i> Règlement</div>
</a>
</li>
<li class="{{ if it.tab === 'membre'}}uk-active{{ /if }}">
<a href="/membre">
<div><i class="fa fa-lock"></i> Membre</div>
</a>
</li>
<li class="{{ if it.tab === 'contact'}}uk-active{{ /if }}">
<a href="/contact">
<div><i class="fa fa-phone"></i> Nous Joindre</div>
</a>
</li>
</ul>
<ul class="uk-navbar-nav uk-visible-medium">
<li class="uk-parent">
<div class="uk-navbar-brand"><a href="https://www.facebook.com/SportsPhenixMtl"><i class="fa fa-facebook-square"></i></a></div>
</li>
<li class="{{ if tab === 'home'}}uk-active{{ /if }}"><a href="/"><i class="fa fa-home"></i> Accueil </a></li>
<li class="{{ if tab === 'nouvelles'}}uk-active{{ /if }}"><a href="/nouvelles"><i class="fa fa-newspaper-o"></i> Nouvelles</a></li>
<li class="{{ if it.tab === 'calendrier'}}uk-active{{ /if }}"><a href="/calendrier"><i class="fa fa-calendar"></i> Calendrier</a></li>
<li class="{{ if it.tab === 'reglement'}}uk-active{{ /if }}"><a href="/reglement"><i class="fa fa-legal"></i> Règlement</a></li>
<li class="{{ if it.tab === 'membre'}}uk-active{{ /if }}"><a href="/membre"><i class="fa fa-lock"></i> Membre</a></li>
<li class="{{ if it.tab === 'contact'}}uk-active{{ /if }}"><a href="/contact"><i class="fa fa-phone"></i> Nous Joindre</a></li>
</ul>
<ul class="uk-navbar-nav uk-visible-small">
<li class="uk-parent">
<div class="uk-navbar-brand"><a href="https://www.facebook.com/SportsPhenixMtl"><i class="fa fa-facebook-square"></i></a></div>
</li>
<li data-uk-dropdown="" aria-expanded="" class="uk-parent"><a><i class="fa fa-bars"></i> Menu</a>
<div class="uk-dropdown">
<ul class="uk-nav uk-nav-navbar uk-dropdown-navbar">
<li class="uk-active"><a href="/"><i class="fa fa-home"></i> Accueil</a></li>
<li class=""><a href="/nouvelles"><i class="fa fa-newspaper-o"></i> Nouvelles</a></li>
<li class=""><a href="/calendrier"><i class="fa fa-calendar"></i> Calendrier</a></li>
<li class=""><a href="/reglement"><i class="fa fa-legal"></i> Règlement</a></li>
<li class=""><a href="/membre"><i class="fa fa-lock"></i> Membre</a></li>
<li class=""><a href="/contact"><i class="fa fa-phone"></i> Nous Joindre</a></li>
</ul>
</div>
</li>
</ul>
</nav>
{{ content }}
<footer class="uk-grid ph-footer" style="padding: 40px;">
<div class="uk-container uk-container-center uk-text-center">
<div class="uk-panel"><span class="uk-hidden-small">Ligue de balle les Phénix... pour le plaisir de jouer!</span>
<h4 class="uk-visible-small">Ligue de balle les Phénix</h4>
</div>
<ul class="uk-subnav uk-subnav-line uk-flex-center">
<li><a href="mailto:sportsphenixmtl@gmail.com">sportsphenixmtl@gmail.com</a></li>
</ul>
<h1><a href="https://www.facebook.com/SportsPhenixMtl"><i class="fa fa-facebook-square"></i></a></h1>
</div>
</footer>
</body>
</html>
+107
View File
@@ -0,0 +1,107 @@
{{ layout "templates/container.vto" }}
<script type="module" src="scripts/little-calendar.js"></script>
<div class="uk-grid">
<div class="uk-large-1-3 uk-medium-2-3 uk-container-center">
<div style="height:300px; width: 300px; background-size: 300px; background-image: url(images/logosansfond.JPG);" class="uk-cover-background uk-container-center uk-margin-left uk-margin-top"></div>
</div>
</div>
<div class="uk-margin-top uk-margin-bottom uk-grid">
<div class="uk-width-large-3-5 uk-width-medium-4-5 uk-width-small-1-1 uk-container-center">
<div class="uk-grid uk-visible-large uk-grid-match">
<div class="uk-width-large-1-3 uk-width-medium-1-3">
<div class="uk-panel uk-panel-box">
<div class="uk-panel-badge uk-badge">
<i class="fa fa-newspaper-o" style="font-size: 1.7em;"></i>
</div>
<div>
{{ include "templates/includes/home-news.vto" }}
</div>
</div>
</div>
<div class="uk-width-large-1-3 uk-width-medium-1-3">
<div class="uk-panel uk-panel-box">
<div class="uk-panel-badge uk-badge"><i class="fa fa-calendar" style="font-size: 1.7em;"></i></div>
<h3 class="uk-panel-title"><a href="#/calendrier" class="uk-link-muted">Calendrier</a></h3>
<div id="large-mithril-container"></div>
</div>
</div>
<div class="uk-width-large-1-3 uk-width-medium-1-3">
<div class="uk-panel uk-panel-box">
<div class="uk-panel-badge uk-badge"><i class="fa fa-map-o" style="font-size: 1.7em;"></i></div>
<h3 class="uk-panel-title">Parc Walter-Stewart</h3>
{{ include "templates/includes/walter-stewart-map.vto" }}
</div>
</div>
</div>
<!-- start -->
<div class="uk-visible-medium">
<div class="uk-grid uk-grid-match">
<div class="uk-width-medium-1-2">
<div class="uk-panel uk-panel-box">
<div class="uk-panel-badge uk-badge"><i class="fa fa-newspaper-o" style="font-size: 1.7em;"></i></div>
<div>
{{ include "templates/includes/home-news.vto" }}
</div>
</div>
</div>
<div class="uk-width-medium-1-2">
<div class="uk-panel uk-panel-box">
<div class="uk-panel-badge uk-badge"><i class="fa fa-calendar" style="font-size: 1.7em;"></i></div>
<h3 class="uk-panel-title"><a href="#/calendrier" class="uk-link-muted">Calendrier</a></h3>
<div id="medium-mithril-container"></div>
</div>
</div>
</div>
<div class="uk-grid">
<div class="uk-width-medium-1-1">
<div class="uk-panel uk-panel-box">
<div class="uk-panel-badge uk-badge"><i class="fa fa-map-o" style="font-size: 1.7em;"></i></div>
<h3 class="uk-panel-title">Parc Walter-Stewart</h3>
{{ include "templates/includes/walter-stewart-map.vto" }}
</div>
</div>
</div>
</div>
<!-- end -->
<div class="uk-visible-small">
<div class="uk-grid">
<div class="uk-width-small-1-1">
<div class="uk-panel uk-panel-box">
<div class="uk-panel-badge uk-badge"><i class="fa fa-newspaper-o" style="font-size: 1.7em;"></i></div>
<div>
{{ include "templates/includes/home-news.vto" }}
</div>
</div>
</div>
</div>
<div class="uk-grid">
<div class="uk-width-small-1-1">
<div class="uk-panel uk-panel-box">
<div class="uk-panel-badge uk-badge"><i class="fa fa-calendar" style="font-size: 1.7em;"></i></div>
<h3 class="uk-panel-title"><a href="#/calendrier" class="uk-link-muted">Calendrier</a></h3>
<div id="small-mithril-container"></div>
</div>
</div>
</div>
<div class="uk-grid">
<div class="uk-width-small-1-1">
<div class="uk-panel uk-panel-box">
<div class="uk-panel-badge uk-badge"><i class="fa fa-map-o" style="font-size: 1.7em;"></i></div>
<h3 class="uk-panel-title">Parc Walter-Stewart</h3>
{{ include "templates/includes/walter-stewart-map.vto" }}
</div>
</div>
</div>
</div>
</div>
</div>
{{ /layout }}
+68
View File
@@ -0,0 +1,68 @@
<div id="game-{{ game.id }}">
{{set prettyGameDate = new Date(game.date).toLocaleString("fr-CA", { month: 'long', year: 'numeric', day: 'numeric', timeZone: 'UTC'}) }}
<h3> {{ game.away }} vs {{ game.home }} | {{ prettyGameDate }} | {{ game.time }}</h3>
<form style="font-size: 1.1em;"
hx-trigger="input delay:250ms"
hx-post="/membre/games/{{game.id}}"
hx-target="#saving-result">
<div class="uk-form-row">
<label>
Points {{ game.away }} : <input type=number
min=0
name="away-score"
value="{{ game.awayScore || 0 }}"
{{if game.rain || game.practice }}disabled{{ /if}}>
</label>
</div>
<div class="uk-form-row">
<label>
Points {{ game.home }} : <input type=number
min=0
name="home-score"
value="{{ game.homeScore || 0 }}"
{{if game.rain || game.practice }}disabled{{ /if}}>
</label>
</div>
<div class="uk-form-row">
<label>
Partie reguliere <input type=radio
name="game-type"
value="regular-game"
{{if ! game.practice && ! game.rain }} checked {{/if}}>
</label>
<label>
Pluie <input type=radio
name="game-type"
value="rain"
{{if game.rain }}checked{{/if}}>
</label>
<label>
Pratique <input
type=radio
name="game-type"
value="practice"
{{if game.practice && ! game.rain }}checked{{/if}}>
</label>
</div>
<div id="saving-result">
</div>
</form>
<div style="text-align: right">
<button class="uk-button-danger"
hx-delete="/membre/games/{{game.id}}"
hx-confirm="Certain de vouloir supprimer la partie?"
hx-target="#game-{{ game.id }}"
hx-swap="delete"
>Supprimer</button>
</div>
</div>
+11
View File
@@ -0,0 +1,11 @@
<h3 class="uk-panel-title">
<a href="#/nouvelles" class="uk-link-muted">
<h2 id="saison-2023">Saison 2023</h2>
</a>
</h3>
<p>
<p>Bonne saison à tous et toutes!</p>
<p>N'oubliez pas de consulter la page facebook: <a href="https://www.facebook.com/SportsPhenixMtl/">https://www.facebook.com/SportsPhenixMtl/</a> pour toutes mises à jour, y compris les annulations due à la météo.</p>
<p><strong><a href="#/nouvelles">lire la suite ...</a></strong></p>
</p>
+10
View File
@@ -0,0 +1,10 @@
{{ set selectedTeam = selectedTeam || "" }}
{{set isDisabled = isDisabled || false }}
{{set teams = ['jaune', 'rouge', 'bleu', 'gris', 'vert', 'noir', 'orange', 'mauve'] }}
<select name="{{- name -}}" class="uk-select" {{if isDisabled}} disabled {{ /if }}>
{{ for team of teams }}
<option name="{{team}}" {{if selectedTeam == team}} selected {{ /if }}>{{ team }}</option>
{{ /for }}
</select>
+15
View File
@@ -0,0 +1,15 @@
<div>
<iframe
style="border: 1px solid black; min-height: 300px;"
width="100%"
frameborder="0"
scrolling="no"
marginheight="0"
src="//www.openstreetmap.org/export/embed.html?bbox=-73.55936229228975%2C45.53102667048665%2C-73.55230271816255%2C45.53444249585723&amp;layer=mapnik"; // "//www.openstreetmap.org/export/embed.html?bbox=-73.56355190277101%2C45.5294483312637%2C-73.54943275451662%2C45.53627996625677&amp;layer=mapnik"; // "//www.openstreetmap.org/export/embed.html?bbox=-73.56355190277101%2C45.5294483312637%2C-73.54943275451662%2C45.53627996625677&amp;layer=mapnik"
></iframe>
<br>
<small>
<a href="http://www.openstreetmap.org/#map=17/45.53216/-73.55692">Voir la carte</a>
</small>
</div>
+28
View File
@@ -0,0 +1,28 @@
{{ layout "templates/container.vto" }}
<div id="content"
{{ if isLoggedIn }}
hx-get="/membre/games-editor/today"
hx-trigger="load"
hx-target="#content"
{{ /if }}
>
<div class="uk-grid uk-margin">
<div class="uk-width-1-1">
<div style="height: 250px; width: 250px; background-size: 250px; background-image: url(images/logosansfond.JPG);" class="uk-cover-background uk-container-center"></div>
</div>
</div>
<div class="uk-panel uk-panel-box uk-panel-box-secondary uk-width-large-1-3 uk-container-center uk-margin">
<form action=""
class="uk-text-center"
hx-get="/login"
hx-target="#content">
<div class="uk-form-row"><label>Nom d'utilisateur <input type="text" name="username" class="uk-form-width-small"></label></div>
<div class="uk-form-row"><label>Mot de passe <input type="password" name="password" class="uk-form-width-small"></label></div>
<div class="uk-form-row"><button class="uk-button"><i class="fa fa-mars-double"></i> Pénétrez</button></div>
</form>
</div>
</div>
{{ /layout }}
+20
View File
@@ -0,0 +1,20 @@
{{ layout "templates/container.vto" }}
<div class="uk-width-large-2-5 uk-width-medium-3-5 uk-width-small-1-1 uk-container-center">
<div>
<article class="uk-article uk-margin-">
<h1 class="uk-article-title">
<h2 id="saison-2023">Saison 2023</h2>
</h1>
<p class="uk-article-meta">
<p>Dimanche 10 Juillet 2023</p>
</p>
<p>Bonne saison à tous et toutes!</p>
<p>N'oubliez pas de consulter la page facebook: <a href="https://www.facebook.com/SportsPhenixMtl/">https://www.facebook.com/SportsPhenixMtl/</a> pour toutes mises à jour, y compris les annulations due à la météo.</p>
<p>Votre Comité 2023</p>
</article>
</div>
</div>
{{ /layout }}
+37
View File
@@ -0,0 +1,37 @@
{{set isToday = !!isToday }}
<div class="uk-width-large-2-3 uk-container-center uk-margin">
<div class="uk-margin" style="margin-top: 1em">
<ul class="uk-tab">
<li {{if isToday}} class="uk-active" {{ /if}}>
<a hx-get="/membre/games-editor/today"
hx-target="#content">
Aujourd'hui
</a>
</li>
{{ for year of years }}
<li {{if year === selectedYear}} class="uk-active" {{ /if}}>
<a hx-get="/membre/games-editor/{{year}}"
hx-target="#content">
Saison {{year}}
</a>
</li>
{{ /for }}
</ul>
</div>
{{ for game of games }}
<div class="uk-panel uk-panel-box uk-panel-box-secondary uk-margin">
{{ include "templates/includes/game-editor.vto" {game} }}
</div>
{{ /for }}
<hr>
<button class="uk-button"
hx-get="/member/new-game-editor"
hx-target="#content">
Nouvelle Partie
</button>
</div>
+7
View File
@@ -0,0 +1,7 @@
<div class="uk-width-large-2-3 uk-container-center uk-margin">
<div class="uk-panel uk-panel-box uk-panel-box-secondary uk-margin">
<pre>{{ error }}</pre>
</div>
</div>
+45
View File
@@ -0,0 +1,45 @@
<div class="uk-width-large-2-3 uk-container-center uk-margin">
<div class="uk-margin"></div>
<div class="uk-panel uk-panel-box uk-panel-box-secondary uk-margin">
<form hx-post="/membre/new-game"
hx-target="#created-game"
hx-swap="afterbegin">
<div class="uk-form-row" style="text-align: center; font-size: 2em;">
{{ include "templates/includes/team-selector.vto" {name: "away-team"} }}
<label>
Vs.
</label>
{{ include "templates/includes/team-selector.vto" {name: "home-team"}}}
</div>
<div class="uk-form-row">
<label>
Date: <input type=date name="game-date" required>
</label>
</div>
<div class="uk-form-row">
<label>
Heure: <input type="time" name="game-time">
</label>
</div>
<br>
<div style="text-align: right;">
<button class="uk-button">Creer</button>
</div>
<form>
</div>
<div id="created-game"></div>
</div>
@@ -0,0 +1,7 @@
<div class="uk-width-large-2-3 uk-container-center uk-margin">
<div class="uk-panel uk-panel-box uk-panel-box-secondary uk-margin">
{{ include "templates/includes/game-editor.vto" {game} }}
</div>
</div>
+42
View File
@@ -0,0 +1,42 @@
{{ layout "templates/container.vto" }}
<div class="uk-margin-top uk-margin-bottom uk-grid">
<div class="uk-width-large-3-5 uk-width-medium-4-5 uk-width-large-1-1 uk-container-center">
<div class="uk-grid">
<div class="uk-width-large-1-3 uk-width-small-1-1">
<div style="height: 250px; width: 250px; background-size: 250px; background-image: url(images/logosansfond.JPG);" class="uk-cover-background uk-container-center"></div>
</div>
<div class="uk-width-large-2-3 uk-width-small-1-1">
<div class="uk-panel uk-panel-box uk-panel-box-secondary">
<h2>Règlements 2021</h2>
<ul>
<li>
<h3><a href="files/regle_de_jeux_2021.pdf">Règles de jeu</a></h3>
</li>
<li>
<h3><a href="files/regles_et_procedures_2021.pdf">Règles et procédures</a></h3>
</li>
<li>
<h3><a href="files/charte_organisationnelle_2021.pdf">Charte Organisationnelle</a></h3>
</li>
<li>
<h3><a href="files/formulaire_inscription_2021.pdf">Formulaire d'inscription</a></h3>
</li>
<li>
<h3><a href="files/code_ethique_2021.pdf">Code d'éthique</a></h3>
</li>
<li>
<h3><a href="http://www.asbm.ca/">Association des Sports de Balle à Montréal (ASBN)</a></h3>
</li>
</ul>
</div>
</div>
</div>
<div class="uk-panel uk-panel-box uk-panel-box-secondary">
<h2>Mission</h2>
<p>La ligue de balle Les Phénix a été fondée en 2004 afin d'offrir aux membres de la communauté gaie et lesbienne et à leurs amis hétéros l'opportunité de s'amuser et de pratiquer un sport dans une ambiance amicale et décontractée. L'ouverture d'esprit, la camaraderie et le plaisir de pratiquer un sport à l'extérieur caractérisent cette ligue.</p>
</div>
</div>
</div>
{{ /layout }}