Skip to main content

CardTrio

A Python terminal client for three courses, backed by your Google Sheet and a Google Apps Script admin dashboard. Learners submit code or text for manual review. An administrator's approval unlocks the next step.

Course Subject Lesson cards Challenges
python96 Python 48 12
BattleAI HTML 48 12
microduck JavaScript 48 12

Every card includes a lesson, an example, and a practice problem. Every fourth card is followed by a challenge. There are 144 cards and 36 challenges in total. This is an original standalone implementation with no ICOA dependency.

1. Set up Google Apps Script

  1. Open your course Google Sheet. Choose Extensions → Apps Script.
  2. Replace the entire previous Code.gs with apps-script/Code.gs from this project. Remove any earlier versions of doGet, doPost, or public admin helpers in other files so they cannot conflict with these handlers.
  3. Add a script file named Curriculum and paste apps-script/Curriculum.gs.
  4. Add an HTML file named Admin and paste apps-script/Admin.html.
  5. Optionally enable “Show appsscript.json manifest file” in project settings and replace it with the supplied apps-script/appsscript.json.
  6. Select setup_ in the editor and run it. Authorize access to the Sheet. The trailing underscore is intentional: it keeps this setup helper private from web-page RPC calls.
  7. Select Deploy → New deployment → Web app. Execute as Me, and allow Anyone to access the endpoint. Learners are authenticated by their course tokens, and admin actions require a server-validated admin session. If your Workspace account does not permit anonymous web-app access, a plain terminal client cannot use that deployment without an additional Google sign-in flow.
  8. Copy the production URL ending in /exec, not /dev.

setup_ seeds the full curriculum automatically; a CSV import is not required. It creates these tabs and validates their headers:

  • Catalog: lessons, practice, challenges, and reference answers.
  • Tokens: token, student, courses, active state, optional expiry.
  • Reviews: submitted work, status, feedback, review time, revision.

The initial admin password is admin. It is hashed with a random salt and stored in Script Properties, not in HTML or the Python client. Re-running setup preserves an existing password and existing data. An existing compatible Catalog is kept as-is rather than overwritten. Keep the Sheet private to its administrators.

For an unbound Apps Script project, set SPREADSHEET_ID in Script Properties to your Sheet ID before running setup_. Do not copy another spreadsheet's ID.

2. Open the admin dashboard

Append ?page=admin to your deployed URL:

https://script.google.com/macros/s/YOUR_DEPLOYMENT_ID/exec?page=admin

Sign in with admin. The dashboard provides:

  • A queue filtered by course and review status, with pagination.
  • Submitted code rendered as text, the problem, lesson context, and a reference answer. Other correct solutions can be approved; exact matching is not required.
  • Approve & unlock next step, with optional feedback.
  • Request changes, requiring actionable feedback. The learner can revise and submit a new attempt. Earlier attempts remain in the ledger.
  • Token issuance for any one course or all three, optional expiration, and enable/disable controls.
  • A Settings page for changing the admin password. This revokes existing admin sessions. Sessions otherwise expire after one hour and can expire earlier if Apps Script evicts its cache. Sign in again when prompted.

The dashboard does not run submitted code. HTML is displayed as text, not rendered as a page. The only network requests made by the learner client target Google Apps Script and its Google-hosted response redirects.

3. Install and run the learner client

Requires Python 3.10 or later. There are no runtime third-party dependencies.

From the extracted project directory:

python -m pip install .
cardtrio configure
cardtrio

For an already-built wheel:

python -m pip install dist/cardtrio_terminal-0.2.0-py3-none-any.whl
cardtrio configure
cardtrio

On Windows, py may be used instead of python. If scripts are not on PATH, use python -m cardtrio and python -m cardtrio configure.

Configure the base /exec URL without ?page=admin. An admin issues access tokens in the dashboard's Access tokens tab, then provides each learner their token. Tokens are reusable access codes, not a consumable credit balance.

Shortcuts:

python96
battleai
microduck
cardtrio --course BattleAI

Tokens are entered with a hidden password prompt and are not saved to disk. CARDTRIO_TOKEN and CARDTRIO_URL can optionally supply login configuration. The endpoint is stored in ~/.cardtrio/config.json. CARDTRIO_HOME overrides the local settings directory.

During a lesson

  • Enter a short answer and press Enter to submit it for review.
  • Use :multi for multiline code. A line containing only . ends input.
  • Use :file PATH to submit a UTF-8 source file after preview and confirmation.
  • Use :hint to revisit the lesson rule.
  • Use :refresh to check for an admin decision.
  • Use :menu to change courses, or :quit to close the program.

Submissions are limited to 8,000 characters. No arbitrary code is executed by the terminal application or backend. A local outbox preserves unconfirmed submissions without storing the token. Network retries reuse the request ID, so a lost response cannot submit the same work twice. If a local retry becomes obsolete, the retry prompt's d option discards only that local retry; it does not cancel work already received by the administrator.

Approval is required before the next step becomes available. Completion is derived from the contiguous sequence of approvals in Reviews, keeping progress and the review decision in one authoritative record. Do not manually reorder or change review statuses unless intentionally repairing data.

Updating an earlier draft

Version 0.2 replaces automatic exact-answer grading with manual review. Earlier Progress and Submissions tabs are not deleted or imported; they remain an archive. Manual-review progress starts in the new Reviews tab. Existing compatible Tokens and Catalog tabs are reused. A mismatched header causes setup to stop rather than replace the sheet's data.

Curriculum maintenance

The authoring source is tools/build_curriculum.py. Regenerate bundled data and the Apps Script seed after editing it:

python tools/build_curriculum.py
python -m cardtrio check
python -m cardtrio export --output Catalog.csv

The CSV export is optional and useful for editing an existing Catalog. Back up the Sheet before replacing content. Do not renumber active course steps because reviews refer to those step numbers. Apps Script source changes require a new deployment version; simply saving the editor does not update a production /exec deployment.

Tests

From a source checkout, install the package first or set PYTHONPATH=src:

python -m unittest discover -s tests -p "test_*.py" -v
node tests/test_backend.cjs

The backend tests execute the actual Apps Script source with in-memory Google service doubles. They cover authentication, token permissions, expiration, manual review, feedback, idempotency, revisions, progression, and header safety. They do not replace a live Google deployment test.

The optional browser test requires Node.js, Playwright, and Chromium:

node tests/test_admin_browser.cjs

It uses the real HTML and backend with service doubles, checks the review and token flows, and saves desktop/mobile screenshots in artifacts/. Set CHROMIUM_PATH if Chromium is not at /usr/bin/chromium.

PyPI release

The working distribution name is cardtrio-terminal. Availability and ownership have not been verified. Choose a name you control in pyproject.toml before publishing. The installed command names can remain unchanged.

python -m pip install build twine
python -m build
python -m twine check dist/*
python -m twine upload --repository testpypi dist/*

After checking TestPyPI and finalizing your package metadata, publish to your PyPI account with python -m twine upload dist/*. Upload credentials belong in your publishing environment, not in this package. No PyPI upload or Google Apps Script deployment is performed merely by installing or running CardTrio.

The MIT license covers this original code and curriculum. There is no ICOA code, content, branding, or service dependency.

References: Python packaging and Apps Script web apps.

Metadata

Release files for cardtrio-terminal 0.2.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for cardtrio-terminal 0.2.0
File Size Uploaded Provenance Actions
cardtrio_terminal-0.2.0.tar.gz 95.9 kB Without provenance Details for cardtrio_terminal-0.2.0.tar.gz

Built distribution (wheel)

Table of built distributions (wheels) for cardtrio-terminal 0.2.0
File Interpreter ABI Platform Actions
cardtrio_terminal-0.2.0-py3-none-any.whl Python 3 none any Details for cardtrio_terminal-0.2.0-py3-none-any.whl

Total release size: 128.1 kB

Release files / cardtrio_terminal-0.2.0.tar.gz

Download URL cardtrio_terminal-0.2.0.tar.gz
Size 95.9 kB
Tags Source
SHA-256 checksum
How to use checksums
12cd430e0123a73b52a5f9711e499dddefa28c2e661f229dbb465b047ede38b7
BLAKE2b-256 checksum
How to use checksums
8106827d02ee0a7da11e406b3e0306db70d2eae90297e4eeab055742527298e2
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.15.2

Release files / cardtrio_terminal-0.2.0-py3-none-any.whl

Download URL cardtrio_terminal-0.2.0-py3-none-any.whl
Size 32.2 kB
Tags Python 3
SHA-256 checksum
How to use checksums
f34589f432d34841f83928b0cff9d497a6e79d78ea615ffc42a4d3056b48a6a5
BLAKE2b-256 checksum
How to use checksums
76e7fee6b7ea6c6ce15e9b3a929a6080e03595f795a49b0bb594009a61fc2fe3
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.15.2

Security for cardtrio-terminal 0.2.0

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

No provenance found

None of the files in this release were uploaded with provenance metadata.

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

This release

0.2.0 This release

2 release files No provenance

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page