Skip to content

Latest commit

 

History

History
338 lines (274 loc) · 8.66 KB

MIGRATION_GUIDE.md

File metadata and controls

338 lines (274 loc) · 8.66 KB

Migration Guide: Version Management Changes

This guide helps you migrate your existing vCon code to work with the updated version management system.

Overview

The vCon library has been updated to align with the latest vCon specification changes. The most significant change is that the version field is now optional and version management has been simplified. All changes are backward compatible, so existing code will continue to work without changes.

Key Changes

Version Field is Now Optional

  • The vcon field is no longer required in vCon objects
  • No automatic version assignment or migration
  • Existing vCons with version fields continue to work unchanged
  • New vCons can be created without version fields

Removed Version Management

  • Removed strict_version parameter from all methods
  • No more automatic version migration
  • No more version enforcement or validation

What's New

vCon Object Level

  • extensions: List of extension names used
  • critical: List of extensions that must be supported

Party Object

  • sip: SIP URI for VoIP communication
  • did: Decentralized Identifier for blockchain-based identity
  • jCard: vCard format contact information
  • timezone: Party's timezone

Dialog Object

  • session_id: Session identifier for tracking conversations
  • content_hash: Hash for content integrity verification (replaces alg/signature)

Migration Steps

Step 1: Update Method Calls (Required if using strict_version)

If you were using the strict_version parameter, you need to remove it:

# Old code (will cause errors)
vcon = Vcon.load("file.json", strict_version=True)
vcon = Vcon.build_from_json(json_str, strict_version=True)
vcon = Vcon(data, strict_version=True)

# New code (remove strict_version parameter)
vcon = Vcon.load("file.json")
vcon = Vcon.build_from_json(json_str)
vcon = Vcon(data)

Step 2: Version Field Handling (Optional)

The version field is now optional. You can choose to:

Option A: Remove version fields from new vCons

# Old code
vcon = Vcon({"uuid": "123", "vcon": "0.4.0", "created_at": "2024-01-01T00:00:00Z"})

# New code (version field optional)
vcon = Vcon({"uuid": "123", "created_at": "2024-01-01T00:00:00Z"})

Option B: Keep existing version fields

# This still works - no changes needed
vcon = Vcon({"uuid": "123", "vcon": "0.4.0", "created_at": "2024-01-01T00:00:00Z"})

Step 3: Add Extensions (Optional)

If you want to declare extension capabilities:

# Old code
vcon = Vcon.build_new()

# New code
vcon = Vcon.build_new()
vcon.add_extension("video")
vcon.add_extension("encryption")
vcon.add_critical("encryption")

Step 2: Enhance Party Information (Optional)

Add additional contact and identification methods:

# Old code
party = Party(
    name="John Doe",
    tel="+1234567890"
)

# New code
party = Party(
    name="John Doe",
    tel="+1234567890",
    sip="sip:john@example.com",
    did="did:example:123456789abcdef",
    jCard={
        "fn": "John Doe",
        "tel": "+1234567890",
        "email": "john@example.com"
    },
    timezone="America/New_York"
)

Step 3: Add Session Tracking (Optional)

Track conversation sessions:

# Old code
dialog = Dialog(
    type="text",
    start=datetime.now(),
    parties=[0, 1],
    body="Hello!"
)

# New code
dialog = Dialog(
    type="text",
    start=datetime.now(),
    parties=[0, 1],
    body="Hello!",
    session_id={"local": "local-uuid", "remote": "remote-uuid"}
)

Step 4: Add Content Integrity (Optional)

Replace alg/signature with content_hash:

# Old code
dialog = Dialog(
    type="text",
    start=datetime.now(),
    parties=[0, 1],
    body="Hello!",
    alg="sha256",
    signature="abc123"
)

# New code
dialog = Dialog(
    type="text",
    start=datetime.now(),
    parties=[0, 1],
    body="Hello!",
    session_id={"local": "local-uuid", "remote": "remote-uuid"}
)

# Calculate and set content hash
content_hash = dialog.calculate_content_hash()
dialog.set_content_hash(content_hash)

Complete Migration Example

Before Migration

from vcon import Vcon
from vcon.party import Party
from vcon.dialog import Dialog
from datetime import datetime

# Create vCon
vcon = Vcon.build_new()

# Add party
party = Party(name="Alice", tel="+1234567890")
vcon.add_party(party)

# Add dialog
dialog = Dialog(
    type="text",
    start=datetime.now(),
    parties=[0],
    body="Hello!"
)
vcon.add_dialog(dialog)

# Save
vcon.save_to_file("conversation.json")

After Migration

from vcon import Vcon
from vcon.party import Party
from vcon.dialog import Dialog
from datetime import datetime

# Create vCon with extensions
vcon = Vcon.build_new()
vcon.add_extension("video")
vcon.add_critical("encryption")

# Add party with enhanced information
party = Party(
    name="Alice",
    tel="+1234567890",
    sip="sip:alice@example.com",
    did="did:example:123456789abcdef",
    jCard={
        "fn": "Alice Johnson",
        "tel": "+1234567890",
        "email": "alice@example.com"
    },
    timezone="America/New_York"
)
vcon.add_party(party)

# Add dialog with session tracking and integrity
dialog = Dialog(
    type="text",
    start=datetime.now(),
    parties=[0],
    body="Hello!",
    session_id={"local": "local-uuid", "remote": "remote-uuid"}
)

# Calculate and set content hash
content_hash = dialog.calculate_content_hash()
dialog.set_content_hash(content_hash)

vcon.add_dialog(dialog)

# Save
vcon.save_to_file("conversation.json")

JSON Output Comparison

Before Migration

{
    "uuid": "...",
    "vcon": "0.4.0",
    "parties": [{
        "name": "Alice",
        "tel": "+1234567890"
    }],
    "dialog": [{
        "type": "text",
        "start": "...",
        "parties": [0],
        "body": "Hello!"
    }]
}

After Migration

{
    "uuid": "...",
    "vcon": "0.4.0",
    "extensions": ["video"],
    "critical": ["encryption"],
    "parties": [{
        "name": "Alice",
        "tel": "+1234567890",
        "sip": "sip:alice@example.com",
        "did": "did:example:123456789abcdef",
        "jCard": {
            "fn": "Alice Johnson",
            "tel": "+1234567890",
            "email": "alice@example.com"
        },
        "timezone": "America/New_York"
    }],
    "dialog": [{
        "type": "text",
        "start": "...",
        "parties": [0],
        "body": "Hello!",
        "session_id": {"local": "local-uuid", "remote": "remote-uuid"},
        "content_hash": "..."
    }]
}

Backward Compatibility

  • Existing code continues to work: All new fields are optional
  • No breaking changes: Existing vCon files will load correctly
  • Gradual adoption: You can add new fields incrementally
  • Property handling: New fields work with all property handling modes (default, strict, meta)

Testing Your Migration

  1. Run existing tests: Ensure they still pass
  2. Test new functionality: Use the example in samples/example_new_fields.py
  3. Validate JSON output: Check that new fields appear correctly
  4. Verify backward compatibility: Load old vCon files to ensure they work

Need Help?

  • Check the full documentation in docs/source/new_required_fields.rst
  • Run the example: python samples/example_new_fields.py
  • Review the test files for usage examples
  • Open an issue if you encounter problems

Migrating to 0.10.0 (draft-ietf-vcon-vcon-core-04)

0.10.0 retargets the library to draft-ietf-vcon-vcon-core-04. The specification's body semantics did not change from prior guidance in this library (a "json"-encoded body was always meant to be a JSON value, not a string), but two behavior changes follow from aligning with the WG's reference JSON schema:

  • Legacy string bodies are now read transparently. If you (or an adapter) previously wrote a "json"-encoded body as a json.dumps string -- for example a tags attachment body written as '["category:support"]' instead of ["category:support"] -- get_tag(), add_tag(), and the lawful-basis/WTF extension validators now decode that string automatically. add_tag() also normalizes a legacy string body back to a list, in place, the first time you call it on that vCon. You don't need to migrate existing data by hand.
  • New attachments get more defaults filled in. add_attachment(), add_lawful_basis_attachment(), and add_wtf_transcription_attachment() now default party/dialog to 0 and start to the vCon's created_at when you don't supply them, because the WG JSON schema requires start, party, and dialog on every attachment. If your code checked for the absence of these keys (rather than their values), check the CHANGELOG's 0.10.0 entry before upgrading.