Skip to Content.
Sympa Menu

cc-licenses - relicensing rules encoded

cc-licenses AT lists.ibiblio.org

Subject: Development of Creative Commons licenses

List archive

Chronological Thread  
  • From: Mike Linksvayer <ml AT creativecommons.org>
  • To: Discussion on the Creative Commons license drafts <cc-licenses AT lists.ibiblio.org>
  • Subject: relicensing rules encoded
  • Date: Mon, 21 Mar 2005 13:05:14 -0800

cc-relicense.py attached

Comments on accuracy desired. Even if you can't read python you can read the rules as explained in comments.

Eventually we may make this available as a web service so people can build Flash toys or whatever to help people visualize how licenses combine.

--
Mike Linksvayer
http://creativecommons.org/about/people#21
# encodes rules for relicensing Creative Commons licensed works
#
# relicense() function contains the logic
#
# combine() accepts multiple licenses, calls relicense() for
# each and returns intersection of allowable licenses
#
# see tests at end for expected values
#
# read comments in relicense() for explanation of rules

import copy

DEBUG = 0
LICENSES =
['by','by-nc','by-nc-nd','by-nc-sa','by-nd','by-sa','nc-sampling+','publicdomain','sampling','sampling+']

def debug(msg):
if (DEBUG):
print msg

# keep only licenses matching 'keep' parameter
def keep(licenses, keep):
for license in copy.copy(licenses):
if (license.find(keep) == -1):
licenses.remove(license)
debug('keep: '+keep+' REMOVED: '+license)
else:
debug('keep: '+keep+' KEPT: '+license)

# remove licenses matching 'remove' parameter
def remove(licenses, remove):
for license in copy.copy(licenses):
if (license.find(remove) != -1):
licenses.remove(license)
debug('remove: '+remove+' REMOVED: '+license)
else:
debug('remove: '+remove+' KEPT: '+license)

# allowed relicensing options for a single license
def relicense(license):
relicenses = copy.copy(LICENSES)
# PD allows anything
if (license.find('publicdomain') != -1):
return relicenses
# sampling requires attribution although 'by' isn't in the URI
if (license.find('by') != -1 or license.find('sampling') != -1):
remove(relicenses,'publicdomain')
# noncommercial must be propagated
if (license.find('nc') != -1):
keep(relicenses,'nc')
# noderivs must be propagated. note that this is only good for
# redistribution of verbatim copies, does not allow derivative works
if (license.find('nd') != -1):
keep(relicenses,'nd')
# sharealike requires exact license match
if (license.find('sa') != -1 and license.find('sampling') == -1):
keep(relicenses,license)
# sampling requires another sampling license to propagate
# no advertising and transformation requirement
# unadorned sampling requires unadorned sampling to propagate
# no verbatim distribution
if (license.find('sampling') != -1):
keep(relicenses, 'sampling')
if (license.find('sampling+') == -1):
remove(relicenses,'sampling+')
return relicenses

# intersection of allowed relicensing options for each license
def combine(licenses):
relicenseset = None
for license in licenses:
thisrelicenseset = set(relicense(license))
if (relicenseset == None):
relicenseset = thisrelicenseset
else:
relicenseset = relicenseset.intersection(thisrelicenseset)
return relicenseset

def test(license, expectedrelicenses):
if (isinstance(expectedrelicenses,set)):
relicenses = combine(license)
else:
relicenses = relicense(license)
if (relicenses == expectedrelicenses):
print 'PASS:', license, 'expected&got:', relicenses
else:
print 'FAIL:', license, 'expected:', expectedrelicenses, 'expected:',
relicenses

# test each license against expected values
test('by',['by','by-nc','by-nc-nd','by-nc-sa','by-nd','by-sa','nc-sampling+','sampling','sampling+'])
test('by-nc',['by-nc','by-nc-nd','by-nc-sa','nc-sampling+'])
test('by-nc-nd',['by-nc-nd'])
test('by-nc-sa',['by-nc-sa'])
test('by-nd',['by-nc-nd','by-nd'])
test('by-sa',['by-sa'])
test('nc-sampling+',['nc-sampling+'])
test('publicdomain',LICENSES)
test('sampling',['sampling'])
test('sampling+',['nc-sampling+','sampling','sampling+'])

# test just a few multi-license combinations
test(['by-nc-sa','nc-sampling+'],set([]))
test(['by-sa','by-nc-sa'],set([]))
test(['by','publicdomain','sampling+'],set(['nc-sampling+','sampling','sampling+']))




Archive powered by MHonArc 2.6.24.

Top of Page