Skip to content

build!: Restructure repo & rename to xblocks-core - #244

Draft
kdmccormick wants to merge 8 commits into
mainfrom
kdmccormick/xblocks-core
Draft

build!: Restructure repo & rename to xblocks-core#244
kdmccormick wants to merge 8 commits into
mainfrom
kdmccormick/xblocks-core

Conversation

@kdmccormick

@kdmccormick kdmccormick commented Apr 29, 2026

Copy link
Copy Markdown
Member

Related

Description

Overview

This PR reshapes the project around two breaking changes: it renames the distribution from xblocks-contrib
to xblocks-core, and it restructures the codebase so each built-in XBlock lives in its own standalone
package under src/.

The changes are broken down by commit, with the major ones highlighted below.

Rename: xblocks-contribxblocks-core

The project was originally named "xblocks-contrib" after django.contrib, but "Contrib" isn't a widely
understood term in Open edX, whereas "Core Blocks" is. Since the project is still new, we're renaming it
now. This updates the PyPI package name, the GitHub repository URL, the development-status classifier (Alpha
→ Production/Stable), and all README and documentation references. No code or file layout changes are part
of the rename itself.

Restructure: one package per XBlock under src/

Previously all built-in XBlocks shared a single xblocks_contrib namespace package
(xblocks_contrib.annotatable, xblocks_contrib.video, etc.), with xblock_pdf as a separate exception.
Each XBlock now lives in its own standalone package under src/:

src/xblock_annotatable/
src/xblock_discussion/
src/xblock_html/
src/xblock_lti/
src/xblock_pdf/
src/xblock_poll_question/
src/xblock_problem/
src/xblock_video/
src/xblock_word_cloud/
src/xblocks_core/          (shared legacy utilities)

Each package has a single block.py entry point, an __init__.py that re-exports the block class, and its
own conf/locale/ and .tx/config for translations. This makes it straightforward to eventually publish
any XBlock as an independently versioned package, and makes it low-risk to add new blocks without changing
their import paths.

A couple of notable details:

  • The poll XBlock becomes xblock_poll_question rather than xblock_poll, because xblock_poll is already
    registered on PyPI by OpenCraft's polling XBlock. The entry-point key was already
    _poll_question_extracted, so consumers using the entry-point API are unaffected — only direct Python
    imports of xblocks_contrib.poll change.
  • Dev and prod static-asset paths are now the same (public/<asset> relative to each block), removing a
    special-case code path that produced different paths in the two environments.

Supporting changes

The remaining commits are follow-on build and cleanup work to support the new layout: updated test and
coverage configuration for the src/ layout, an explicit webpack-merge dev dependency, a
package-lock.json regeneration to pick up the pdf-block Vitest dependency tree, a ruff format pass,
and removal of a redundant pip install from the docs tox environment.

BREAKING CHANGES (across all commits)

  • The distribution is renamed from xblocks-contrib to xblocks-core.
  • Direct Python imports move from the shared xblocks_contrib.* namespace to per-block packages (e.g.
    xblocks_contrib.pollxblock_poll_question). Consumers using the XBlock entry-point API are unaffected.

AI

Opus did the first-pass restructuring. Feanil and I both added fixes of our own. I reviewed all changes line-by-line/

The git history became a mess, so I used Sonnet to split it back up into multiple commits.

Testing

Needs to be tested with the accompanying platform PR:

I validated that this works with dev settings on my machine using my bare-metal setup.

I validated that this works with prod settings using the sandbox on the linked openedx-platform PR.

Testing process:

  • import demo course
  • add block types which are not in the demo course: pdf, lti, poll_question, annotatable?, discussion?, word_cloud?, survey?
  • import demo course content into a V2 content library
  • ensure a block of each type can be edited, previewed, and published from the library.
  • in a new course, add a block of each type from the library.
  • ensure each block can be edited and previewed. publish all.
  • view in LMS. ensure they can be viewed and, if relevent, submitted.
  • downloadable test course: (download link)

@kdmccormick
kdmccormick force-pushed the kdmccormick/xblocks-core branch from cbb0348 to e92b6ed Compare April 29, 2026 13:55
@@ -14,7 +14,7 @@ <h3 class="hd hd-2">{{ display_name|escape }}</h3>
data-block-id='{{ block_id|escape }}'
data-course-id='{{ course_id|escape }}'
tabindex="-1"
data-package-name="xblocks-contrib">
data-package-name="xblocks-core">

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does this matter?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The only mention of this is in this file and I didn't see any mention of this in the openedx-platform history so I have no idea.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We added it for testing purpose to differentiate between BuiltIn and Extracted Block at brower.

  • renaming with repo sounds good.
  • We can remove it after removal of BuiltIn blocks, removing now seems alright as well as we are pretty much done with the major testing.

Comment thread src/xblock_word_cloud/.tx/config
@kdmccormick
kdmccormick force-pushed the kdmccormick/xblocks-core branch 3 times, most recently from 86c65f3 to 5fbbf35 Compare April 29, 2026 16:10
@kdmccormick
kdmccormick force-pushed the kdmccormick/xblocks-core branch from a70e618 to a91002d Compare April 29, 2026 17:03
@kdmccormick
kdmccormick force-pushed the kdmccormick/xblocks-core branch from bd1ae1d to 76dd6bc Compare May 4, 2026 19:26
runs-on: ubuntu-latest
strategy:
fail-fast: true
fail-fast: false

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
fail-fast: false
fail-fast: true

Note to self: Undo this before merging

@kdmccormick
kdmccormick force-pushed the kdmccormick/xblocks-core branch 2 times, most recently from fe1f184 to 7a9efbf Compare May 4, 2026 20:04
@kdmccormick
kdmccormick marked this pull request as ready for review May 4, 2026 20:06
@kdmccormick
kdmccormick requested a review from feanil May 4, 2026 20:07
@kdmccormick

Copy link
Copy Markdown
Member Author

@feanil Tests all pass on this locally. I'm still manually testing and waiting on GHA to catch up, but feel free to take a look if you have time. You can review commit-by-commit.

@kdmccormick
kdmccormick force-pushed the kdmccormick/xblocks-core branch 3 times, most recently from fbe6c1c to ba3dc09 Compare May 5, 2026 16:34

@feanil feanil left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I tried to do as thorough a review as I could on this big change, but there are a lot of moving parts so the openedx-platform testing will be critical for this. That said, a not for other reviewers is that the consolidated diff makes reading the translations changes a bit confusing since it makes it seem like translations conf files were move around in between blocks. But looking at the commit diffs it's more obvious what's going on.

@@ -14,7 +14,7 @@ <h3 class="hd hd-2">{{ display_name|escape }}</h3>
data-block-id='{{ block_id|escape }}'
data-course-id='{{ course_id|escape }}'
tabindex="-1"
data-package-name="xblocks-contrib">
data-package-name="xblocks-core">

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The only mention of this is in this file and I didn't see any mention of this in the openedx-platform history so I have no idea.

@kdmccormick

Copy link
Copy Markdown
Member Author

Thanks @feanil !

Per my latest testing, this is working fine on tutor dev, but failing on tutor local:

Screenshot 2026-05-07 at 11 18 24 AM

I'll hold off until merging until I can fix local.

@farhan farhan left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM!

Skipped translations code review as it needs to work on it later on.

Comment thread README.rst Outdated

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
* Done: The built-in block has been removed. The setup.py entrypoint has been removed from edx-platform and added to xblock-core.

@farhan
farhan self-requested a review June 22, 2026 07:18
@kdmccormick
kdmccormick force-pushed the kdmccormick/xblocks-core branch from 376c4da to 8b0aa19 Compare August 5, 2026 18:29
@kdmccormick
kdmccormick force-pushed the kdmccormick/xblocks-core branch 2 times, most recently from e183482 to e35a81f Compare August 10, 2026 18:12
@kdmccormick kdmccormick changed the title build: Restructure repo & rename to xblocks-core build!: Restructure repo & rename to xblocks-core Aug 10, 2026
kdmccormick and others added 7 commits August 10, 2026 14:54
The src/xblock_pdf/js_tests workspace (pdf-block) declares vitest, vite,
@vitest/browser-playwright, and typescript as devDependencies, but
package-lock.json was not regenerated to include their dependency tree.
This left the lock out of sync with the workspace's package.json, so
`npm ci` would fail. Regenerate the lock to add the missing (dev-only)
transitive dependencies.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
The repository was originally named "xblocks-contrib", inspired by
"django.contrib", which is a collection of nonessential but widely
used django modules such as django.contrib.auth. But, the "Contrib"
the term is not widely understood in Open edX, whereas "Core Blocks"
is a widely understood concept. So, we've decided to rename the project
while it's still new.

This commit updates the PyPI package name, the GitHub repository URL,
the development status classifier (Alpha → Production/Stable), the
README title, and all documentation references. Code and file layout are
unchanged here; the module restructuring follows in the next commit.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Related: #149
Each XBlock now lives in its own standalone package under src/. Previously,
all built-in XBlocks shared a single xblocks_contrib namespace package
(xblocks_contrib.annotatable, xblocks_contrib.video, etc.), with xblock_pdf
as a separate exception. The new layout is:

  src/xblock_annotatable/
  src/xblock_discussion/
  src/xblock_html/
  src/xblock_lti/
  src/xblock_pdf/
  src/xblock_poll_question/
  src/xblock_problem/
  src/xblock_video/
  src/xblock_word_cloud/
  src/xblocks_core/          (shared legacy utilities)

Each package has a single block.py entry point, an __init__.py that
re-exports the block class, and its own conf/locale/ and .tx/config for
translations. This makes it straightforward to eventually publish any
XBlock as a separate, independently versioned package, if that is ever
desired. It also is also now possible and low-risk to add new blocks in
(e.g. xblock_drag_and_drop_v2) without changing their improt path.

The poll XBlock becomes xblock_poll_question rather than xblock_poll because
the name xblock_poll is already registered on PyPI by OpenCraft's polling
XBlock (https://github.com/open-craft/xblock-poll), which has a different
feature set. The entry-point key was already _poll_question_extracted, so
consumers using the entry-point API are unaffected; only direct Python
imports of xblocks_contrib.poll change.

Dev and prod static-asset paths are now the same (public/<asset> relative
to each block), removing a special-case code path that produced different
paths in the two environments.

Related: #237

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
The discussion and problem XBlock webpack configs use the webpack-merge v5
API to combine shared and environment-specific configuration objects. Webpack-
merge was previously available only as a transitive dependency, so it was not
guaranteed to be at the right major version. Adding it explicitly as a direct
devDependency ensures the correct version is installed regardless of what
other packages happen to pull in.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Now that all packages live under src/, pytest and coverage need to know to
look there rather than at the old top-level xblocks_contrib/ and xblock_pdf/
directories.

On the pytest side: add "." and "src" to pythonpath so that test_settings.py
(at the repo root) and the new src/xblock_*/ packages are both importable
without an editable install. Add "build" to norecursedirs so that any
compiled artifacts under build/lib/ are not mistakenly collected as test
modules. Update --cov to point at src so that coverage is reported across all
packages in one pass.

On the coverage side: set source = ["src"] for the same reason.

Tox already runs pytest with "src" as the positional argument, which is
unchanged here; this commit focuses on the ini-level defaults that apply
whether you run pytest directly or through tox.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
The docs environment uses uv-venv-lock-runner with package = true, so the
project is already installed when tox sets up the virtual environment. The
pip install -e . call was not present on main and is not needed. It was also
causing a tox failure because pip is not listed in allowlist_externals for
that environment.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@kdmccormick
kdmccormick force-pushed the kdmccormick/xblocks-core branch from 563f2b3 to 269c3d2 Compare August 10, 2026 19:03
@kdmccormick
kdmccormick marked this pull request as draft August 10, 2026 19:21
@kdmccormick
kdmccormick force-pushed the kdmccormick/xblocks-core branch from 495d816 to 269c3d2 Compare August 10, 2026 20:12
The previous commits had updated package-lock.json on macOS,
which caused it to be broken on other platforms like CI.
This regenerates package-lock.json from scratch on Ubuntu 24.04.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants