Package: runestone
Packaging of the Runestone components for publishing educational materials using Sphinx and restructuredText. Check out theOverviewTo see all of the extensions in action.Runestone Version 7ImportantMay 2023 moved RunestoneComponents repository to a new monorepo for the whole project.To build a release of runestone including the javascript for the interactive components, use the build.py script in this folder.pythonbuild.pyTo build a release and publish that release to PyPI use the--publishoptionpythonbuild.py--publishThe publish option assumes you have the credentials to publish on pyPI, as well as credentials for the runestone load balancer.DocumentationWritingnewbooks using the Runestone RST markup language is deprecated as of Summer 2022.  It is strongly recommended that you use thePreTeXtmarkup language for writing new books.Take a look at theSample Book <https://pretextbook.org/examples/sample-book/annotated/sample-book.html>Especially Chapter 3, the section titled Interactive Exercises.  The activecode, CodeLens and all the rest of the interactives that you see in that sample book are powered by the components in this repository.  This repository will remain the home of those interctive components.Take a look at thePreTeXt GuideIt contains comprehensive documentation on writing in PreTeXt.As an Author you will want to use the PreTeXt CLI for writing books.   Experienced Runestone authors will find the pretext cli to be quite familiar, but better organized with fewer mysterious configuration files. SeePreTeXt-CLI <https://pretextbook.org/doc/guide/html/guide-toc.html>Quick Startpip install pretextCreate a folder for your book project then runpretext newto create a new book.Old DocumentationI will keep this around for a while during the transition to PreTeXt.To get started with Runestone restructuredText as the markup language:pip install runestoneTo start a project, create a new folder and then run the following command (installed by pip)  in that new folderrunestone initFor example:mkdirmyprojectcdmyprojectrunestoneinitThe init command will ask you some questions and setup a default project for you. The default response is in square brackets, example[false].To build the included default project runrunestonebuildNote:If you come across version conflict withsixlibrary while building the project,pip install--ignore-installedsixcommand might be useful.You will now have a build folder with a file index.html in it, along with some default content.  The contents of the build folder are suitable for hosting anywhere that you can serve static web content from!  For a small class you could even serve the content using the provided Python webserver:$runestoneserveNow from your browser you can open uphttp://localhost:8000/index.htmlYou should see the table of contents for a sample page like this:If you edit_sources/index.htmlor_sources/overview.rstand then rebuild and serve again you will see your changes.  The best documentation is probably the overview.rst file itself, as it demonstrates how to use all of the common components and shows most of their options.Windows UsersI have tested the installation, along with init, build, and serve on Windows 8.1.
The biggest pain is probably setting your PATH environment variable so you can simply type the commands
from the shell.  Please note that I am not a regular user of windows, I only test things on my VMWare
installation every so often.  If you are new to using Python on windows I recommend you check out this
link onUsing Python with WindowsDeveloping and HackingSo, you would like to help out with developing the Runestone Components.  Great We welcome all the help we can get.  There is plenty to do no matter what your experience level.  There are a couple of prerequisites.You will need a version of Python, I currently develop on 3.9 or higher, but test on 3.8 and later.You will need nodejs and npm as well since there is a LOT of Javascript code in the components.To get everything set up do the followingMake a Fork of this repository. andgit clonethe repository to your development machine.InstallPoetryFrom the top level RunestoneComponents folder runnpm installthis will install the packaging tools that are needed for Javascript development.npm rungives you a list of commands  The key command isnpm run buildthis will combine all of the Javascript and CSS files for all the components into a single runestone.js file.  If you are doing some really deep development and want to avoid building a book, you can put your html in public/index.html and use thenpm run startcommand.  This will automatically rebuild runestone.js and refresh the webpage every time you save a change.When you have some changes to share, make a Pull Request.(See the RunestoneServer repository andhttp://runestoneinteractive.orgfor more complete documentation on how this project works.)Code StyleWe useblackto automatically style Python.  You can set up your editor to automatically run black whenever you save, or you can run it manually.We useprettierto automatically style Javascript.Runjshinton your code we have some options configured for this project.Writing TestsA great way to contribute to the Runestone Components repository is to add to our test suite.Our goal is to have unit tests which rely on Selenium (a library that helps simulate interactions in a web browser) for each directive, to see if the JavaScript that powers the directives is working correctly.In order to get started with writing a test/writing additional tests, you will need the following:Download the latestChromeDriver., which is a driver that simulates Google Chrome.On linux you will need to install Xvfbapt-getinstall xvfbYou’ll also need to have done the above installation.We have converted to using poetry for our dependency management.  To runrunestonewhile in development modepoetry run runestone …OR you can runpoetry shellto start up a shell with a virtual environment activated.To run tests:Make sure the directory containing the ChromeDriver executable is in yourPATHenvironment variable. e.g.PATH=$PATH:path/to/chromedriverat your command line (or edit your.bash_profile).Check out the existing tests, e.g. thetest_question.pyfile that tests the Question directive, which you can find at the path/runestone/question/test/test_question.py, for an example.Each directive’s individual set of tests requires a mini book. You’ll see a_sourcesfolder for each existing test containing anindex.rstfile. That file contains a title, as required by.rst, and whatever directive examples you want to test.Finally, to run a test, ensuring that you have accessed a directive folder, type the following at the command prompt:poetry run pytestRunning pytest from the main directory will run all the tests.  To run a single test you can navigate to the
directory of the test, or you can runpoetry run pytest-kXXXwhere XXX is a substring that matches some part of
the test functions name.Note8081 is the default test port.
If you are running another server on this port, you may encounter an error.
See the Python files, e.g.test_question.py, to see how this is set up.You should then see some test output, showing a pass (ok), FAIL, or error(s).If you have an error relating to PhantomJS/a driver in the output, you probably have a PATH or driver installation problem.To write a new test:Create atestdirectory inside a directive’s folderCreate a Python file to hold the test suite inside that directory, e.g.test_directivename.pyRunrunestone initinside that folder and answer the following promptsWrite the appropriate directive example(s) inside theindex.rstfile (which will be created as a result ofrunestone init)Edit the Python file you created as appropriate (see documentation for the PythonunittestmoduleIn the Python docs.)Notes for more Advanced UsersIf you already have an existingSphinxproject and you want to incorporate the runestone components into your project you can just make a couple of simple edits to your existingconf.pyfile.First add the following import linefrom runestone import runestone_static_dirs, runestone_extensionsThen modify your extensions.  You may have a different set of extensions already enabled, but it doesn’t matter just do this:extensions = ['sphinx.ext.mathjax'] + runestone_extensions()Then modify your html_static_path:html_static_path = ['_static']  + runestone_static_dirs()Again you may have your own set of static paths in the initial list.Seehttps://github.com/bnmnetp/runestone/wiki/DevelopmentRoadmapto get a sense for how this is all going to come together.ResearchersIf you use Runestone in your Research or write about it, please referencehttps://runestone.academyand cite this paper:@inproceedings{Miller:2012:BPE:2325296.2325335,author={Miller, Bradley N. and Ranum, David L.},title={Beyond PDF and ePub: Toward an Interactive Textbook},booktitle={Proceedings of the 17th ACM Annual Conference on Innovation and Technology in Computer Science Education},series={ITiCSE '12},year={2012},isbn={978-1-4503-1246-2},location={Haifa, Israel},pages={150--155},numpages={6},url={http://doi.acm.org/10.1145/2325296.2325335},doi={10.1145/2325296.2325335},acmid={2325335},publisher={ACM},address={New York, NY, USA},keywords={cs1, ebook, sphinx},}