From 5cd55e65afddf015c40ac16f688f753a5d80e95f Mon Sep 17 00:00:00 2001 From: Claude Date: Thu, 23 Oct 2025 20:01:14 +0000 Subject: [PATCH] docs: Add comprehensive Wiki.js version compatibility documentation MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add detailed compatibility documentation and version detection: - Add Wiki.js 2.x compatibility badge and requirements to README - Create comprehensive docs/compatibility.md guide - Detailed version support matrix (2.2 through 2.5.308+) - API schema differences between 2.x and 3.x - Version detection examples and troubleshooting - Known compatibility issues and solutions - Future 3.x support planning - Enhance test_connection() in both sync and async clients - Add API version compatibility detection - Better error messages for incompatible versions - Detect Wiki.js 3.x and provide clear guidance - Update package metadata - Add Wiki.js compatibility keywords to setup.py and pyproject.toml - Add compatibility documentation link to project URLs SDK supports Wiki.js 2.x (versions 2.2 - 2.5.308+) Wiki.js 3.x (alpha) not yet supported due to different API schema 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude --- README.md | 24 ++- docs/compatibility.md | 405 ++++++++++++++++++++++++++++++++++++++++++ pyproject.toml | 4 +- setup.py | 4 +- wikijs/aio/client.py | 38 +++- wikijs/client.py | 38 +++- 6 files changed, 496 insertions(+), 17 deletions(-) create mode 100644 docs/compatibility.md diff --git a/README.md b/README.md index a803a9a..5a3f2a8 100644 --- a/README.md +++ b/README.md @@ -2,6 +2,7 @@ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT) [![Python Support](https://img.shields.io/badge/python-3.8+-blue.svg)](https://python.org) +[![Wiki.js Support](https://img.shields.io/badge/Wiki.js-2.2+-green.svg)](https://docs.requarks.io/releases) [![Repository](https://img.shields.io/badge/repo-Gitea-green.svg)](https://gitea.hotserv.cloud/lmiranda/py-wikijs) [![Issues](https://img.shields.io/badge/issues-Gitea-blue.svg)](https://gitea.hotserv.cloud/lmiranda/py-wikijs/issues) @@ -50,6 +51,21 @@ new_page = client.pages.create(PageCreate( --- +## 📋 Requirements + +### System Requirements +- **Python**: 3.8 or higher +- **Wiki.js**: 2.2 or higher (tested with 2.5.x series) +- **API Access**: Valid API key with appropriate permissions + +### Compatibility Notes +> **✅ Supported**: This SDK is designed for **Wiki.js 2.x** (versions 2.2 through 2.5.308+) +> **⚠️ Not Supported**: Wiki.js 3.x (alpha) uses a different API schema and is not yet supported + +For detailed compatibility information, see [docs/compatibility.md](docs/compatibility.md). + +--- + ## 🎯 Current Development Status ### **Phase 1: MVP Development** ✅ **COMPLETE** @@ -76,6 +92,8 @@ new_page = client.pages.create(PageCreate( ### **For Users** - **[Quick Start](#quick-start)**: Basic setup and usage +- **[Requirements](#requirements)**: System and Wiki.js version requirements +- **[Compatibility Guide](docs/compatibility.md)**: Detailed version compatibility information - **[API Reference](docs/api_reference.md)**: Complete SDK documentation - **[User Guide](docs/user_guide.md)**: Comprehensive usage guide with examples - **[Examples](examples/)**: Real-world usage examples and code samples @@ -111,9 +129,11 @@ We welcome contributions! This project showcases systematic development with pro ## 🛠️ Development Setup ### Prerequisites -- Python 3.8+ +See [Requirements](#requirements) for system and Wiki.js version requirements. + +Additional development tools: - Git -- Wiki.js instance for testing +- Wiki.js 2.x instance for testing (2.2 or higher) ### Local Development ```bash diff --git a/docs/compatibility.md b/docs/compatibility.md new file mode 100644 index 0000000..7cff8e0 --- /dev/null +++ b/docs/compatibility.md @@ -0,0 +1,405 @@ +# Wiki.js Compatibility Guide + +**Last Updated**: October 2025 +**SDK Version**: v0.1.0+ + +--- + +## 📋 Overview + +This document provides detailed information about Wiki.js version compatibility for the py-wikijs Python SDK. + +--- + +## ✅ Supported Versions + +This SDK is compatible with **Wiki.js 2.x** (version 2.2 and higher). + +### Tested Versions + +| Wiki.js Version | Status | Notes | +|-----------------|--------|-------| +| **2.5.308** | ✅ Fully Tested | Current stable release | +| **2.5.x series** | ✅ Supported | All 2.5.x versions | +| **2.4.x series** | ✅ Supported | Limited testing | +| **2.3.x series** | ✅ Supported | Limited testing | +| **2.2.x series** | ✅ Supported | API baseline version | +| **2.0 - 2.1** | ⚠️ Partial | Missing API features | +| **1.x series** | ❌ Not Supported | Legacy version | +| **3.x (alpha)** | ❌ Not Supported | Different API schema | + +### Version Requirements + +**Minimum Requirements:** +- **Wiki.js**: 2.2 or higher +- **Python**: 3.8 or higher +- **API Access**: API key authentication enabled + +**Recommended:** +- **Wiki.js**: 2.5.x (latest stable) +- **Python**: 3.10 or higher +- **Permissions**: Full admin API key for complete functionality + +--- + +## 🔍 API Version Details + +### Wiki.js 2.x API Schema + +This SDK uses the **Wiki.js 2.x GraphQL API schema**, which features nested query structure: + +```graphql +# Pages API (2.x) +query { + pages { + list(limit: 10) { + id + title + path + } + } +} + +# Users API (2.x) +query { + users { + list { + id + name + email + } + } +} + +# Groups API (2.x) +query { + groups { + list { + id + name + permissions + } + } +} + +# Assets API (2.x) +query { + assets { + list { + id + filename + fileSize + } + } +} +``` + +### Key API Features by Version + +| Feature | Version Added | SDK Support | +|---------|---------------|-------------| +| **GraphQL API** | 2.0 | ✅ | +| **API Key Authentication** | 2.2 | ✅ | +| **Pages API** | 2.2 | ✅ Full CRUD | +| **Users API** | 2.2 | ✅ Full CRUD | +| **Groups API** | 2.2 | ✅ Full CRUD | +| **Assets API** | 2.2 | ✅ Full management | +| **Page Rules** | 2.3 | ✅ Supported | +| **Batch Operations** | N/A | ✅ SDK feature | +| **Auto-Pagination** | N/A | ✅ SDK feature | + +--- + +## ⚠️ Not Supported: Wiki.js 3.x + +### Why 3.x Is Not Supported + +Wiki.js 3.x (currently in alpha) introduces **breaking API changes**: + +1. **Flattened GraphQL Schema**: Queries moved to root level +2. **Different Naming Convention**: `users.list` → `usersList` +3. **Modified Response Format**: Different data structures +4. **New Authentication Methods**: Updated auth flow + +### Example 3.x API Difference + +```graphql +# Wiki.js 2.x (Supported) +query { + pages { + list { id title } + } +} + +# Wiki.js 3.x (Not Supported) +query { + pagesList { id title } +} +``` + +### When Will 3.x Be Supported? + +Support for Wiki.js 3.x will be considered when: +- ✅ 3.x reaches stable/beta status (no ETA yet) +- ✅ API schema is finalized +- ✅ Community adoption begins + +**Planned Approach**: Release as separate major version (v2.0.0 or v3.0.0) with dual support strategy. + +--- + +## 🔧 Version Detection + +### Automatic Compatibility Check + +The SDK includes automatic version detection in the `test_connection()` method: + +```python +from wikijs import WikiJSClient + +client = WikiJSClient('https://wiki.example.com', auth='your-api-key') + +try: + if client.test_connection(): + print("✅ Compatible Wiki.js version detected") +except Exception as e: + print(f"❌ Compatibility issue: {e}") +``` + +### Manual Version Check + +To manually verify your Wiki.js version: + +```python +from wikijs import WikiJSClient + +client = WikiJSClient('https://wiki.example.com', auth='your-api-key') + +# Test with a simple query +try: + pages = client.pages.list(limit=1) + print(f"✅ API compatible - found {len(pages)} page(s)") +except Exception as e: + print(f"❌ API incompatible: {e}") +``` + +### GraphQL Introspection + +You can also check the API schema directly: + +```python +client = WikiJSClient('https://wiki.example.com', auth='your-api-key') + +# Query for API schema information +query = """ +query { + __schema { + queryType { + name + } + } +} +""" + +try: + response = client._request("POST", "/graphql", json_data={"query": query}) + print(f"API Schema: {response}") +except Exception as e: + print(f"Schema check failed: {e}") +``` + +--- + +## 🚀 Feature Compatibility Matrix + +### Core Features + +| Feature | Wiki.js 2.2 | Wiki.js 2.3 | Wiki.js 2.4 | Wiki.js 2.5 | +|---------|-------------|-------------|-------------|-------------| +| Pages CRUD | ✅ | ✅ | ✅ | ✅ | +| Users CRUD | ✅ | ✅ | ✅ | ✅ | +| Groups CRUD | ✅ | ✅ | ✅ | ✅ | +| Assets Management | ✅ | ✅ | ✅ | ✅ | +| Page Rules | ⚠️ Basic | ✅ | ✅ | ✅ | +| Batch Operations | ✅ | ✅ | ✅ | ✅ | +| Async Support | ✅ | ✅ | ✅ | ✅ | +| Caching | ✅ | ✅ | ✅ | ✅ | + +### SDK Features (Version Independent) + +These features work across all supported Wiki.js versions: + +- ✅ **Synchronous Client**: Full support +- ✅ **Async Client**: Full support with aiohttp +- ✅ **Type Safety**: Pydantic models with validation +- ✅ **Error Handling**: Comprehensive exception hierarchy +- ✅ **Retry Logic**: Exponential backoff on failures +- ✅ **Connection Pooling**: Efficient HTTP connections +- ✅ **Batch Operations**: SDK-level batch processing +- ✅ **Auto-Pagination**: Seamless iteration over large datasets +- ✅ **Caching**: LRU cache with TTL support + +--- + +## 🐛 Known Compatibility Issues + +### Issue 1: API Key Permissions + +**Affected Versions**: All +**Symptom**: 403 Forbidden errors on certain operations +**Cause**: Insufficient API key permissions +**Solution**: Ensure API key has appropriate permissions for the operations you need + +```python +# Test permissions +try: + pages = client.pages.list() # Requires read permission + client.pages.create(...) # Requires write permission + client.users.list() # Requires admin permission +except PermissionError as e: + print(f"Permission denied: {e}") +``` + +### Issue 2: GraphQL Rate Limiting + +**Affected Versions**: 2.4+ +**Symptom**: 429 Too Many Requests +**Cause**: Too many API calls in short time +**Solution**: Use SDK's built-in retry logic or implement rate limiting + +```python +from wikijs import WikiJSClient +from wikijs.cache import MemoryCache + +# Enable caching to reduce API calls +cache = MemoryCache(ttl=300) +client = WikiJSClient( + 'https://wiki.example.com', + auth='your-api-key', + cache=cache +) +``` + +### Issue 3: Large File Uploads + +**Affected Versions**: All +**Symptom**: Timeout or memory errors on large asset uploads +**Cause**: Default timeout too short for large files +**Solution**: Increase timeout for upload operations + +```python +# Increase timeout for large uploads +client = WikiJSClient( + 'https://wiki.example.com', + auth='your-api-key', + timeout=300 # 5 minutes +) + +# Upload large file +with open('large-file.pdf', 'rb') as f: + asset = client.assets.upload(f, folder_id=1) +``` + +--- + +## 📊 Compatibility Testing + +### How We Test Compatibility + +1. **Unit Tests**: Test against mocked API responses +2. **Integration Tests**: Test against live Wiki.js 2.5.x instance +3. **Manual Testing**: Periodic testing against 2.4.x and 2.3.x +4. **Community Reports**: User feedback on different versions + +### Running Compatibility Tests + +```bash +# Run full test suite +pytest + +# Run integration tests only +pytest -m integration + +# Run with specific Wiki.js version +WIKIJS_VERSION=2.5.308 pytest -m integration +``` + +### Reporting Compatibility Issues + +If you encounter compatibility issues: + +1. **Check this guide** for known issues +2. **Verify Wiki.js version**: Ensure you're running 2.2+ +3. **Test with examples**: Try SDK examples first +4. **Report issue**: Include Wiki.js version, SDK version, and error details + +--- + +## 🔮 Future Compatibility + +### Planned Support + +| Version | Status | Timeline | +|---------|--------|----------| +| **Wiki.js 2.6+** | ✅ Planned | Automatic (same API) | +| **Wiki.js 3.0** | 📅 Future | When 3.0 reaches beta | +| **Backward Compat** | ✅ Committed | Will maintain 2.x support | + +### Migration Strategy for 3.x + +When Wiki.js 3.x becomes stable: + +1. **Dual Support**: Maintain both 2.x and 3.x compatibility +2. **Version Detection**: Auto-detect Wiki.js version +3. **Clear Documentation**: Migration guide for 3.x users +4. **Gradual Transition**: Long deprecation period for 2.x + +Example future API: + +```python +# Future: Automatic version detection +from wikijs import WikiJSClient + +# Will work with both 2.x and 3.x +client = WikiJSClient('https://wiki.example.com', auth='key') + +# Or force specific version +from wikijs.v2 import WikiJSClient as WikiJSClientV2 +from wikijs.v3 import WikiJSClient as WikiJSClientV3 + +client_v2 = WikiJSClientV2(...) # Force 2.x API +client_v3 = WikiJSClientV3(...) # Force 3.x API +``` + +--- + +## 📞 Support + +### Getting Help + +- **Documentation**: [Full documentation](../README.md) +- **Examples**: [Usage examples](../examples/) +- **Issues**: [Report compatibility issues](https://gitea.hotserv.cloud/lmiranda/py-wikijs/issues) + +### Resources + +- **Wiki.js Documentation**: https://docs.requarks.io/ +- **Wiki.js Releases**: https://docs.requarks.io/releases +- **Wiki.js GraphQL API**: https://docs.requarks.io/dev/api +- **Community Forum**: https://github.com/requarks/wiki/discussions + +--- + +## 📝 Version History + +| SDK Version | Min Wiki.js | Max Wiki.js | Notes | +|-------------|-------------|-------------|-------| +| **0.1.0** | 2.2 | 2.5.308+ | Initial release | +| **0.2.0** | 2.2 | 2.5.308+ | Added async support | + +--- + +**Last Updated**: October 2025 +**Next Review**: When Wiki.js 3.0 beta is released + +For the latest compatibility information, always check this guide or visit the [project repository](https://gitea.hotserv.cloud/lmiranda/py-wikijs). diff --git a/pyproject.toml b/pyproject.toml index 30496dd..c60f944 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -30,7 +30,7 @@ dependencies = [ "typing-extensions>=4.0.0", ] dynamic = ["version"] -keywords = ["wiki", "wikijs", "api", "sdk", "client", "http", "rest"] +keywords = ["wiki", "wikijs", "wiki.js", "api", "sdk", "client", "http", "rest", "graphql", "wiki.js-2.x"] [project.optional-dependencies] dev = [ @@ -64,6 +64,8 @@ Homepage = "https://gitea.hotserv.cloud/lmiranda/py-wikijs" "Bug Reports" = "https://gitea.hotserv.cloud/lmiranda/py-wikijs/issues" Source = "https://gitea.hotserv.cloud/lmiranda/py-wikijs" Documentation = "https://gitea.hotserv.cloud/lmiranda/py-wikijs/src/branch/main/docs" +Compatibility = "https://gitea.hotserv.cloud/lmiranda/py-wikijs/src/branch/main/docs/compatibility.md" +"Wiki.js" = "https://js.wiki" [tool.setuptools.dynamic] version = {attr = "wikijs.version.__version__"} diff --git a/setup.py b/setup.py index a4fb4d2..7f89f45 100644 --- a/setup.py +++ b/setup.py @@ -54,6 +54,8 @@ setup( "Bug Reports": "https://gitea.hotserv.cloud/lmiranda/py-wikijs/issues", "Source": "https://gitea.hotserv.cloud/lmiranda/py-wikijs", "Documentation": "https://gitea.hotserv.cloud/lmiranda/py-wikijs/src/branch/main/docs", + "Compatibility": "https://gitea.hotserv.cloud/lmiranda/py-wikijs/src/branch/main/docs/compatibility.md", + "Wiki.js": "https://js.wiki", }, packages=find_packages(), include_package_data=True, @@ -84,6 +86,6 @@ setup( "Topic :: Documentation", "Typing :: Typed", ], - keywords=["wiki", "wikijs", "api", "sdk", "client", "http", "rest"], + keywords=["wiki", "wikijs", "wiki.js", "api", "sdk", "client", "http", "rest", "graphql", "wiki.js-2.x"], zip_safe=False, ) \ No newline at end of file diff --git a/wikijs/aio/client.py b/wikijs/aio/client.py index c85fb5d..eb4210f 100644 --- a/wikijs/aio/client.py +++ b/wikijs/aio/client.py @@ -278,19 +278,24 @@ class AsyncWikiJSClient: return parse_wiki_response(data) async def test_connection(self) -> bool: - """Test connection to Wiki.js instance. + """Test connection to Wiki.js instance and verify API compatibility. This method validates the connection by making an actual GraphQL query to the Wiki.js API, ensuring both connectivity and authentication work. + It also performs basic API version compatibility detection. Returns: - True if connection successful + True if connection successful and API version is compatible Raises: - ConfigurationError: If client is not properly configured + ConfigurationError: If client is not properly configured or API version incompatible ConnectionError: If cannot connect to server AuthenticationError: If authentication fails TimeoutError: If connection test times out + + Note: + This SDK is designed for Wiki.js 2.x (2.2+). Wiki.js 3.x uses a different + API schema and is not yet supported. """ if not self.base_url: raise ConfigurationError("Base URL not configured") @@ -299,7 +304,8 @@ class AsyncWikiJSClient: raise ConfigurationError("Authentication not configured") try: - # Test with minimal GraphQL query to validate API access + # Test with minimal GraphQL query to validate API access and version + # This query uses the 2.x nested structure query = """ query { site { @@ -315,12 +321,28 @@ class AsyncWikiJSClient: # Check for GraphQL errors if "errors" in response: error_msg = response["errors"][0].get("message", "Unknown error") + + # Check if error indicates API version mismatch + if "Cannot query field" in error_msg or "Unknown type" in error_msg: + raise ConfigurationError( + f"Incompatible Wiki.js API version detected. " + f"This SDK requires Wiki.js 2.2 or higher (2.x series). " + f"Wiki.js 3.x is not yet supported. Error: {error_msg}" + ) + raise AuthenticationError(f"GraphQL query failed: {error_msg}") - # Verify we got expected data structure + # Verify we got expected data structure (2.x format) if "data" not in response or "site" not in response["data"]: - raise APIError("Unexpected response format from Wiki.js API") + # This might indicate a 3.x API or completely different API + raise ConfigurationError( + "Incompatible Wiki.js API detected. " + "This SDK requires Wiki.js 2.x (version 2.2 or higher). " + "Wiki.js 3.x uses a different API schema and is not yet supported. " + "See docs/compatibility.md for more information." + ) + # Connection successful and API version compatible return True except AuthenticationError: @@ -335,6 +357,10 @@ class AsyncWikiJSClient: # Re-raise connection errors as-is raise + except ConfigurationError: + # Re-raise configuration errors as-is + raise + except APIError: # Re-raise API errors as-is raise diff --git a/wikijs/client.py b/wikijs/client.py index b890575..67af338 100644 --- a/wikijs/client.py +++ b/wikijs/client.py @@ -243,19 +243,24 @@ class WikiJSClient: return parse_wiki_response(data) def test_connection(self) -> bool: - """Test connection to Wiki.js instance. + """Test connection to Wiki.js instance and verify API compatibility. This method validates the connection by making an actual GraphQL query to the Wiki.js API, ensuring both connectivity and authentication work. + It also performs basic API version compatibility detection. Returns: - True if connection successful + True if connection successful and API version is compatible Raises: - ConfigurationError: If client is not properly configured + ConfigurationError: If client is not properly configured or API version incompatible ConnectionError: If cannot connect to server AuthenticationError: If authentication fails TimeoutError: If connection test times out + + Note: + This SDK is designed for Wiki.js 2.x (2.2+). Wiki.js 3.x uses a different + API schema and is not yet supported. """ if not self.base_url: raise ConfigurationError("Base URL not configured") @@ -264,7 +269,8 @@ class WikiJSClient: raise ConfigurationError("Authentication not configured") try: - # Test with minimal GraphQL query to validate API access + # Test with minimal GraphQL query to validate API access and version + # This query uses the 2.x nested structure query = """ query { site { @@ -278,16 +284,30 @@ class WikiJSClient: # Check for GraphQL errors if "errors" in response: error_msg = response["errors"][0].get("message", "Unknown error") + + # Check if error indicates API version mismatch + if "Cannot query field" in error_msg or "Unknown type" in error_msg: + raise ConfigurationError( + f"Incompatible Wiki.js API version detected. " + f"This SDK requires Wiki.js 2.2 or higher (2.x series). " + f"Wiki.js 3.x is not yet supported. Error: {error_msg}" + ) + raise AuthenticationError( f"GraphQL query failed: {error_msg}" ) - # Verify we got expected data structure + # Verify we got expected data structure (2.x format) if "data" not in response or "site" not in response["data"]: - raise APIError( - "Unexpected response format from Wiki.js API" + # This might indicate a 3.x API or completely different API + raise ConfigurationError( + "Incompatible Wiki.js API detected. " + "This SDK requires Wiki.js 2.x (version 2.2 or higher). " + "Wiki.js 3.x uses a different API schema and is not yet supported. " + "See docs/compatibility.md for more information." ) + # Connection successful and API version compatible return True except AuthenticationError: @@ -302,6 +322,10 @@ class WikiJSClient: # Re-raise connection errors as-is raise + except ConfigurationError: + # Re-raise configuration errors as-is + raise + except APIError: # Re-raise API errors as-is raise