This repository contains documentation for developers including:
- Writing Scrapers using Pupa
- Open Civic Data's Data Type Specifications
- Open Civic Data Proposals
Read these docs at https://open-civic-data.readthedocs.io/en/latest/
python utilities for Open Civic Data
License: BSD 3-Clause "New" or "Revised" License
This repository contains documentation for developers including:
Read these docs at https://open-civic-data.readthedocs.io/en/latest/
a few of the migrations created are pretty bad/pointless but there is a bug preventing squashing them in Django right now.
since nobody is depending on this yet, prior to a 'real' release we should reset the migrations, preferably when Django 1.7 comes out.
since things are still in flux as a result of the OCDEP process this can wait until 1.0 (or whatever release comes right before it)
should be classification?
needs an enum?
('amendment-introduction', 'Amendment Passage'),
('amendment-passage', 'Amendment Passage'),
('amendment-withdrawal', 'Amendment Withdrawal'),
('amendment-failure', 'Amendment Failure'),
('amendment-amended', 'Amendment Amended'),
Would any of these be appropriate for 'Amended in Committee'? https://chicago.legistar.com/LegislationDetail.aspx?ID=1990715&GUID=F7B80D9B-99C4-4E62-91C5-EE5B977167B1
Question: @paultag I'm a little confused about the difference between merging and what we currently call name-matching. How do they differ in OCDworld?
With the blessing of relevant parties I'd like to start work on an 0.7.x branch (and release a new 0.6.4 as necessary)
I'd propose the following:
Sunlight & anyone else running an instance could pin their systems to use 0.6.x for the time being, but 0.7.x would represent the future w/ working JSONfield & fewer deprecated dependencies on things like djorm-pgarray. Once it has stable models a migration script could be written (likely outside the migration framework for practical reasons)
Here is a stripped down example:
from opencivicdata.core.models import Organization
from opencivicdata import merge
org1 = Organization.objects.create(name='org1')
org2 = Organization.objects.create(name='org2')
merge.merge(org1, org2)
Yield this error:
~/.virtualenvs/django-calaccess-processed-data-py3/src/python-opencivicdata/opencivicdata/merge.py in merge(obj1, obj2)
126
127 def merge(obj1, obj2):
--> 128 diff = compute_diff(obj1, obj2)
129 apply_diff(obj1, obj2, diff)
130
~/.virtualenvs/django-calaccess-processed-data-py3/src/python-opencivicdata/opencivicdata/merge.py in compute_diff(obj1, obj2)
46 })
47 else:
---> 48 related_name = field.get_accessor_name()
49 piece_one = list(getattr(obj1, related_name).all())
50 piece_two = list(getattr(obj2, related_name).all())
AttributeError: 'ForeignKey' object has no attribute 'get_accessor_name'
Looks like there are two fields missing the get_accessor_name
method:
related_fields = [f for f in org1._meta.get_fields() if f.is_relation]
for field in related_fields:
if not getattr(field, "get_accessor_name", None):
print(field)
Yields:
core.Organization.parent
core.Organization.jurisdiction
Hi,
New to this project and admiring the work. We're mirroring parts of this schema in our own elections rig at Politico with the hope we'll eventually be able to adopt the full spec.
Had some some proposals for adding to the Division model to start. Happy to submit a PR once the concepts make sense.
In the docs there is a concept of boundaries. It might make sense to add a Boundary model that foreign keys to Division. A Boundary object would have starting and ending effective dates and a flag representing whether that boundary is the current geographic representation of the Division, letting you have multiple historical representations, useful for modeling congressional districts. It would have a JSONField for keeping Geo/topoJSON directly on the model.
Wondering if we can handle the relationships in the DivisionManager through more explicit models: Many Divisions are hierarchical, country > state > county > precinct. Could a Division have a self-referencing foreign key to a parent Division. Some relationships aren't hierarchical, like congressional district <> county/precinct. Could Divisions capture that relationship with a self-referencing ManyToMany field of intersecting divisions. Making it a m2m through a another model would let you hang the actual proportion of the intersection, which is useful for apportioning things like census counts.
Could the many subtype fields be more easily handled with a JSONField?
Could there also be a higher level abstraction on Division that represents the level of that division. Examples might be a state, a county, a precinct, etc. The major benefit of modeling those levels is it lets us query down from all of a type of Division. Give me the boundaries of all states, for example. This might need to be raised on the docs repo, just let me know.
Thanks. Looking forward to contributing to this.
It would be less confusing for the field to be named "vote_event".
The following package (0.4.5) https://pypi.python.org/pypi/opencivicdata/
doesn't include division-ids, while pupa references it. See opencivicdata/pupa#100
at some point...
Here are some actions I'm not sure how to classify:
'Direct Introduction' seems to refer to legislation that was directly introduced to committe. I.e. not referred from the council to the committee.
'Remove Co-Sponsor(s)' https://chicago.legistar.com/LegislationDetail.aspx?ID=2073840&GUID=CB56231A-805A-4E3C-95D1-43EBD935959B
'Held in Committee'
'Deferred and Published'
While setting up python-opencivicdata-django
for openstates/openstates-pupa
I got this error.
Obtaining python-opencivicdata from git+https://github.com/opencivicdata/python-opencivicdata-django.git#egg=python-opencivicdata
Cloning https://github.com/opencivicdata/python-opencivicdata-django.git to /opt/openstates/venv-pupa/src/python-opencivicdata
- Running setup.py (path:/opt/openstates/venv-pupa/src/python-opencivicdata/setup.py) egg_info for package python-opencivicdata produced metadata for project name opencivicdata-django. Fix your #egg=python-opencivicdata fragments.
Collecting Django>=1.9 (from opencivicdata-django)
Downloading Django-1.10.6-py2.py3-none-any.whl (6.8MB)
Collecting psycopg2 (from opencivicdata-django)
Downloading psycopg2-2.7.1-cp35-cp35m-manylinux1_x86_64.whl (2.7MB)
Collecting opencivicdata-divisions (from opencivicdata-django)
Downloading opencivicdata-divisions-2017.3.22.tar.gz (2.4MB)
Building wheels for collected packages: opencivicdata-divisions
Running setup.py bdist_wheel for opencivicdata-divisions: started
Running setup.py bdist_wheel for opencivicdata-divisions: finished with status 'done'
Stored in directory: /root/.cache/pip/wheels/d4/16/22/543c321bb47ba44dc64843b65e519d407c1a7b9ba50cbd2175
Successfully built opencivicdata-divisions
Installing collected packages: Django, psycopg2, opencivicdata-divisions, opencivicdata-django
Running setup.py develop for opencivicdata-django
Complete output from command /opt/openstates/venv-pupa/bin/python3 -c "import setuptools, tokenize;__file__='/opt/openstates/venv-pupa/src/python-opencivicdata/setup.py';f=getattr(tokenize, 'open', open)(__file__);code=f.read().replace('\r\n', '\n');f.close();exec(compile(code, __file__, 'exec'))" develop --no-deps:
Traceback (most recent call last):
File "<string>", line 1, in <module>
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/setuptools/__init__.py", line 12, in <module>
import setuptools.version
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/setuptools/version.py", line 1, in <module>
import pkg_resources
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/pkg_resources/__init__.py", line 2927, in <module>
@_call_aside
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/pkg_resources/__init__.py", line 2913, in _call_aside
f(*args, **kwargs)
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/pkg_resources/__init__.py", line 2952, in _initialize_master_working_set
add_activation_listener(lambda dist: dist.activate())
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/pkg_resources/__init__.py", line 956, in subscribe
callback(dist)
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/pkg_resources/__init__.py", line 2952, in <lambda>
add_activation_listener(lambda dist: dist.activate())
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/pkg_resources/__init__.py", line 2515, in activate
declare_namespace(pkg)
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/pkg_resources/__init__.py", line 2097, in declare_namespace
_handle_ns(packageName, path_item)
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/pkg_resources/__init__.py", line 2047, in _handle_ns
_rebuild_mod_path(path, packageName, module)
File "/opt/openstates/venv-pupa/lib/python3.5/site-packages/pkg_resources/__init__.py", line 2066, in _rebuild_mod_path
orig_path.sort(key=position_in_sys_path)
AttributeError: '_NamespacePath' object has no attribute 'sort'
----------------------------------------
Command "/opt/openstates/venv-pupa/bin/python3 -c "import setuptools, tokenize;__file__='/opt/openstates/venv-pupa/src/python-opencivicdata/setup.py';f=getattr(tokenize, 'open', open)(__file__);code=f.read().replace('\r\n', '\n');f.close();exec(compile(code, __file__, 'exec'))" develop --no-deps" failed with error code 1 in /opt/openstates/venv-pupa/src/python-opencivicdata/
The command '/bin/sh -c /opt/openstates/venv-pupa/bin/pip install -e git+https://github.com/opencivicdata/python-opencivicdata-django.git#egg=python-opencivicdata' returned a non-zero code: 1
Reticketed from opencivicdata/pupa#225
I'm working an OpenStates issue that leads me here.
In importing a bill via pupa, the exception pupa.exceptions.DataImportError: duplicate key value violates unique constraint "opencivicdata_voteevent_bill_action_id_key"
is being evoked. I infer that this is caused by the same bill action being on two different votes for the same bill, probably enforced by DDL generated by this line. If the exception is really something else entirely, read no further, sorry to waste your time.
This is happening on a bill with a loop in its process; it was re-referred to committee after going to the floor. As a result, some bill actions were duplicated.
I can see two ways to go to fix this, but don't have the use-case experience to recommend one over the other.
One fix is to leave the model as is, and require data generators like OpenStates to synthesize unique bill actions. For example, in the example linked above, the two occurrences of 2nd Reading Passed
might become [2nd Reading Passed
, 2nd Reading Passed (2)
].
The other fix would be to relax the uniqueness requirement here.
if we want Postgres' JSON we may want to move away, this is a known issue. rpkilby/jsonfield#80
for now I've pinned the jsonfield version to 0.9.20 which doesn't have a problem, but we're getting weird errors on 0.9.22 (on travis) where the JSONField comes back as '{}' instead of {}
so that we can throw the bits here back on disk and export in a targz. Also a method to load the dumps.
currently the length is 10, YYYY-MM-DD, should extend to allow optional time
EventDocument should be a subclass of RelatedBase not MimetypeRelatedBase. The intent is fairly clear that links are supposed be on EventDocumentLink
The New Hampshire and Massachusetts constitutions allow for a "Bill of Address" by which a judge can be removed from office. It's very similar to impeachment; both houses have to vote up the address.
There's currently no bill classification corresponding to such a bill, or for any impeachment, in the bill classification list. Should there be?
As far as I can tell, the term "Bill of Address" is peculiar to NH and MA. I don't know how many other states have judicial impeachment, and under what name. Many appear to have gubernatorial impeachment.
the pinned Django version is currently the RC of 1.7, with 1.8's release it is probably time to address that (if this takes longer than expected we should at least move to 1.7.7)
Right now I have a branch @ https://github.com/opencivicdata/python-opencivicdata-django/tree/django1.8
Three outstanding questions on the ArrayField front:
Otherwise, errors.
Different kinds of votes in different legislatures require different percentages of support to pass. Seems like important information to store about a vote - more important than shoving it into extra attributes. The @opencongress
congress scrapers include this attribute in votes as you can see in the following example.
{
"requires": "1/2",
"result": "Failed",
"result_text": "Failed"
}
The result_text
may also be relevant too since we're storing passing as a boolean value instead of the actual text specific to the vote type. This may make more sense though to push to extra attributes.
I think part of the reason we missed some of the mistakes that resulted in PR #106 was that the Travis CI builds were succeeding, showing green checkmarks, but when you drill into the individual jobs, we found the purest failures.
Any ideas why this might be happening? Nothing obvious was jumping out for me.
@@ -43,7 +45,7 @@ class ContactDetailInline(admin.TabularInline):
class OtherNameInline(admin.TabularInline):
- fields = ('name', 'note', 'start_date', 'end_date')
+ #fields = ('name', 'note', 'start_date', 'end_date')
extra = 0
verbose_name = "Alternate name"
verbose_name_plural = "Alternate names"
We recently switched from installing our fork of this repo to the package distributed on PyPi. When running our integration tests in a Python 2.7 environment, we get an ImportError
because backports.csv
is missing. Here's the full stack trace:
Traceback (most recent call last):
File "calaccess_processed/tests/test_commands.py", line 85, in setUpClass
call_command("processcalaccessdata", verbosity=3, noinput=True)
File "/home/travis/virtualenv/python2.7.13/lib/python2.7/site-packages/django/core/management/__init__.py", line 130, in call_command
return command.execute(*args, **defaults)
File "/home/travis/virtualenv/python2.7.13/lib/python2.7/site-packages/django/core/management/base.py", line 356, in execute
output = self.handle(*args, **options)
File "calaccess_processed/management/commands/processcalaccessdata.py", line 64, in handle
self.load()
File "calaccess_processed/management/commands/processcalaccessdata.py", line 92, in load
no_color=self.no_color,
File "/home/travis/virtualenv/python2.7.13/lib/python2.7/site-packages/django/core/management/__init__.py", line 113, in call_command
command = load_command_class(app_name, command_name)
File "/home/travis/virtualenv/python2.7.13/lib/python2.7/site-packages/django/core/management/__init__.py", line 40, in load_command_class
module = import_module('%s.management.commands.%s' % (app_name, name))
File "/opt/python/2.7.13/lib/python2.7/importlib/__init__.py", line 37, in import_module
__import__(name)
File "calaccess_processed/management/commands/loadocdelections.py", line 12, in <module>
from opencivicdata.core.management.commands.loaddivisions import load_divisions
File "/home/travis/virtualenv/python2.7.13/lib/python2.7/site-packages/opencivicdata/core/management/commands/loaddivisions.py", line 6, in <module>
from opencivicdata.divisions import Division as FileDivision
File "/home/travis/virtualenv/python2.7.13/lib/python2.7/site-packages/opencivicdata/divisions.py", line 8, in <module>
from backports import csv
ImportError: cannot import name csv
Guess I didn't have as great a handle on conditional dependencies as I thought...
If I set up a Python 2.7 env, and pip install opencivicdata
, this will install from the wheel:
$ pip install opencivicdata
Collecting opencivicdata
Using cached opencivicdata-2.0.0-py2.py3-none-any.whl
Requirement already satisfied: Django>=1.9 in /Users/gordo/.pyenv/versions/2.7.13/envs/test-django-ocd/lib/python2.7/site-packages (from opencivicdata)
Requirement already satisfied: six in /Users/gordo/.pyenv/versions/2.7.13/envs/test-django-ocd/lib/python2.7/site-packages (from opencivicdata)
Requirement already satisfied: psycopg2 in /Users/gordo/.pyenv/versions/2.7.13/envs/test-django-ocd/lib/python2.7/site-packages (from opencivicdata)
Requirement already satisfied: pytz in /Users/gordo/.pyenv/versions/2.7.13/envs/test-django-ocd/lib/python2.7/site-packages (from Django>=1.9->opencivicdata)
Installing collected packages: opencivicdata
Successfully installed opencivicdata-2.0.0
And backports.csv
is not be included. It's also not mentioned in the distribution's metadata:
cat $VIRTUAL_ENV/lib/python2.7/site-packages/opencivicdata-2.0.0.dist-info/METADATA
Metadata-Version: 2.0
Name: opencivicdata
Version: 2.0.0
Summary: python opencivicdata library
Home-page: UNKNOWN
Author: James Turk
Author-email: [email protected]
License: BSD
Platform: any
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: BSD License
Classifier: Natural Language :: English
Classifier: Operating System :: OS Independent
Classifier: Programming Language :: Python :: 2.7
Classifier: Programming Language :: Python :: 3.4
Classifier: Programming Language :: Python :: 3.5
Classifier: Programming Language :: Python :: 3.6
Requires-Dist: Django (>=1.9)
Requires-Dist: psycopg2
Requires-Dist: six
Provides-Extra: dev
Requires-Dist: coveralls; extra == 'dev'
Requires-Dist: flake8; extra == 'dev'
Requires-Dist: pytest (>=2.9); extra == 'dev'
Requires-Dist: pytest-cov; extra == 'dev'
Requires-Dist: pytest-django; extra == 'dev'
UNKNOWN
Everything works fine, though, if you switch from wheel to egg:
pip install opencivicdata --no-binary :all:
Collecting opencivicdata
Using cached opencivicdata-2.0.0.tar.gz
Requirement already satisfied: six in /Users/gordo/.pyenv/versions/2.7.13/envs/test-django-ocd/lib/python2.7/site-packages (from opencivicdata)
Requirement already satisfied: Django>=1.9 in /Users/gordo/.pyenv/versions/2.7.13/envs/test-django-ocd/lib/python2.7/site-packages (from opencivicdata)
Requirement already satisfied: psycopg2 in /Users/gordo/.pyenv/versions/2.7.13/envs/test-django-ocd/lib/python2.7/site-packages (from opencivicdata)
Collecting backports.csv (from opencivicdata)
Using cached backports.csv-1.0.5.tar.gz
Requirement already satisfied: pytz in /Users/gordo/.pyenv/versions/2.7.13/envs/test-django-ocd/lib/python2.7/site-packages (from Django>=1.9->opencivicdata)
Skipping bdist_wheel for opencivicdata, due to binaries being disabled for it.
Skipping bdist_wheel for backports.csv, due to binaries being disabled for it.
Installing collected packages: backports.csv, opencivicdata
Running setup.py install for backports.csv ... done
Running setup.py install for opencivicdata ... done
Successfully installed backports.csv-1.0.5 opencivicdata-2.0.0
I figure this is because this process actually runs setup.py
, which is where we check if it's a Python 2 environment.
When building a wheel, though, I believe this extra requirement is appended only if your use python setup.py bdist_wheel
in a Python 2 environment.
First, to be clear- it could still be one repository (or not.. depending on what we decide)
That said, it might make sense to separate this out into multiple django apps, I'm thinking something like:
core.models -> People, Organization, etc. (essentially popolo & support models)
legislative.models -> Bill, VoteEvent, etc.
campaign_finance.models -> PR #81
elections.models -> PR #82
I know this came up briefly before but I feel like looking at the potential scope of the new models we should discuss this
I'm working on filling out @aepton's implementation of the Campaign Finance enhancement proposal, and I've uncovered an issue @jamesturk might need to consider sooner rather than later.
In the campaign finance OCDEP, Committee
is described as a "Subclass of Popolo Organization", and adds a couple of attributes not expected on the base class. The existing OCD Organization
class is a non-abstract model, and my understanding is that, as a general rule, we don't want to subclass non-abstract models.
This is similar to the Event
/Election
situation we got into previously. The solution then was to partially copy the definition of the Event
model and create a new Election
model. We also copied the definitions of the EventIdentifier
and EventSource
models to make new ElectionIdentifier
and ElectionSource
models.
I'm following this same approach for Committee
and it's related models, but a few things give me pause:
Event
was in the legislative
module and was tailored to those use cases, Organization
is in the core
module and is defined rather generically.Organization
has a couple of other related model that Committee
also needs:
OrganizationIdentifier
for storing alternate ids for the campaign finance committeeOrganizationName
for storing the committee's various different namesMembership
and Post
for storing relationships committees and their treasurers, officers, staff, etc.OrganizationSource
and OrganizationContactDetails
Transaction
has a .sender
and .recipient
each of which will have either a .person
or .organization
attribute populated, depending on the entity type. Under the current pattern, I think we also need a .committee
attribute, since these can also send and receive transactions.If 4 is a real need, then it feels like exactly what Django's multi-table inheritance was designed for. Even if it isn't, multi-table inheritance would also address the issues raised in 2 and 3.
note people's imports/etc. won't change since the namespace package already worked like this
Reticketed from opencivicdata/pupa#237
It's BSD in setup.py, but an actual LICENSE file will make it clearer.
There are types of documents and media very commonly associated with legislative events:
For downstream work, it would be very helpful to be able to get a document or media by type instead of having it infer it from the name or contents of the document.
@jamesturk, what do you think. If acceptable, I'll make a PR.
this came up before: opencivicdata/pupa#167
The issue being that for data quality purposes it is quite useful to know how many members can simultaneously hold a post.
Ballotpedia has a good summary of their use in US States: https://ballotpedia.org/State_legislative_chambers_that_use_multi-member_districts
Two proposals had come up before: either specifying two or more 'Posts' or specifying a 'maximum' attribute. My current thinking is that multiple posts would be hard to distinguish between and the maximum property would work best here.
Are there objections to going forward w/ this? Have others tackled this in a way they're happy with in the last couple of years since it was first discussed?
classification
in Jurisdiction
, total count emptyDisclosure
checks go in here?)Jurisdiction
, by number of "bad" cellsdocument version classifications that is
I love the idea of this library, but I'm curious to know why the models aren't configured with abstract=True
in their Meta
settings. Am I correct to assume that without that setting, the base models are now all created as tables in the database by Django? If I'm off in left field please just let me know and I will slink back in my cave.
In Chicago, we have some types of legislation that are not in the bill classification choices: https://github.com/opencivicdata/python-opencivicdata-django/blob/master/opencivicdata/common.py#L72
Specifically: order, ordinance, claim, communication, reports, oaths of offices
order seems is the simplest case, since you already have 'concurrent order' in the classification choices. I made a PR to add 'order'
ordinance is a trickier case. It is basically a synonym for 'bill'. Should I record Chicago ordinances as bills?
'claims' are claims by made against the city that are handled, for some reason, by the city council. i.e. https://chicago.legistar.com/LegislationDetail.aspx?ID=2099242&GUID=E2F7C2B5-327B-4D1B-AA2D-BA7D4331A5F4 These seem like a type that should be added.
'communication' Are a sundry of committee reports, notifications of contracts and other events by the executive, resignsations, etc. These are not voted on, but are entered into the journal of proceedings. Not sure what should be done here. There are also 'reports' I am really unsure about the difference between 'reports' and 'communications'.
'Oaths of offices', these seem different than appointments, which we also have.
The Event
Django model currently has a jurisdiction
foreign key field with a not null constraint. However, this field is not mentioned in the OCD Event format or in the Event OCDEP.
Assuming the typical use case is to model meetings of various public agencies (e.g., a state legislative committee or city council), couldn't that be handled via an Organization
as an event participant?
Requires pgarray >= 1.0, I think (0.10 was raising some odd errors)
For some reason, I was getting integer[]
database tables, so I did this locally:
diff --git a/opencivicdata/models/bill.py b/opencivicdata/models/bill.py
index 4a2ffc1..1823f01 100644
--- a/opencivicdata/models/bill.py
+++ b/opencivicdata/models/bill.py
@@ -1,5 +1,5 @@
from django.db import models
-from djorm_pgarray.fields import ArrayField
+from djorm_pgarray.fields import TextArrayField
from .base import (OCDBase, LinkBase, OCDIDField, RelatedBase, RelatedEntityBase, MimetypeLinkBase,
IdentifierBase)
@@ -16,8 +16,8 @@ class Bill(OCDBase):
title = models.TextField()
from_organization = models.ForeignKey(Organization, related_name='bills', null=True)
- classification = ArrayField(dbtype="text") # check that array values are in enum?
- subject = ArrayField(dbtype="text")
+ classification = TextArrayField(dbtype="text") # check that array values are in enum?
+ subject = TextArrayField(dbtype="text")
def __str__(self):
return '{} in {}'.format(self.name, self.legislative_session)
@@ -45,7 +45,7 @@ class BillAction(RelatedBase):
organization = models.ForeignKey(Organization, related_name='actions')
description = models.TextField()
date = models.CharField(max_length=10) # YYYY[-MM[-DD]]
- classification = ArrayField(dbtype="text") # enum
+ classification = TextArrayField(dbtype="text") # enum
order = models.PositiveIntegerField()
class Meta:
I'm not sure if this is still something that matters. I think everyone else (and travis) has this working right, so I can't quite tell if this was just due to having 0.10
installed. I'm about to test, but I'm filing this bug to keep track of that thought.
Just talked this over with @paultag — am I correct that there is no model for amendments? If there is none, how can we help get one started?
I'd like to propose a few new additional bill action classifiers --
I'm looking at doing a few more international scrapers in the future, so may have more later.
Should I just do a PR, have the discussion here, or post it elsewhere? Happy to move this wherever appropriate.
The image field on Person and Organization models are only for a URL string. It seems metadata attributing credit or name of the source for the photo (GPO Member Guide) and a possible note (e.g. "Official Congress Headshot") would provide more complete information about the photo.
Something about the pseduo-upsert we did made Django sad. We shoud be able to explain this, and eventually file a bug / fix with Django.
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.