Beispiel #1
0
// Version of FixJSONNumbers (see base/util.go) that operates on a Body
func (body Body) FixJSONNumbers() {
	for k, v := range body {
		body[k] = base.FixJSONNumbers(v)
	}
}
Beispiel #2
0
// HTTP handler for a POST to _bulk_docs
func (h *handler) handleBulkDocs() error {
	body, err := h.readJSON()
	if err != nil {
		return err
	}
	newEdits, ok := body["new_edits"].(bool)
	if !ok {
		newEdits = true
	}

	userDocs, ok := body["docs"].([]interface{})
	if !ok {
		err = base.HTTPErrorf(http.StatusBadRequest, "missing 'docs' property")
		return err
	}
	lenDocs := len(userDocs)
	// split out local docs, save them on their own
	localDocs := make([]interface{}, 0, lenDocs)
	docs := make([]interface{}, 0, lenDocs)
	for _, item := range userDocs {
		doc := item.(map[string]interface{})
		docid, _ := doc["_id"].(string)
		if strings.HasPrefix(docid, "_local/") {
			localDocs = append(localDocs, doc)
		} else {
			docs = append(docs, doc)
		}
	}

	h.db.ReserveSequences(uint64(len(docs)))

	result := make([]db.Body, 0, len(docs))
	for _, item := range docs {
		doc := item.(map[string]interface{})
		docid, _ := doc["_id"].(string)
		var err error
		var revid string
		if newEdits {
			if docid != "" {
				revid, err = h.db.Put(docid, doc)
			} else {
				docid, revid, err = h.db.Post(doc)
			}
		} else {
			revisions := db.ParseRevisions(doc)
			if revisions == nil {
				err = base.HTTPErrorf(http.StatusBadRequest, "Bad _revisions")
			} else {
				revid = revisions[0]
				err = h.db.PutExistingRev(docid, doc, revisions)
			}
		}

		status := db.Body{}
		if docid != "" {
			status["id"] = docid
		}
		if err != nil {
			code, msg := base.ErrorAsHTTPStatus(err)
			status["status"] = code
			status["error"] = base.CouchHTTPErrorName(code)
			status["reason"] = msg
			base.Logf("\tBulkDocs: Doc %q --> %d %s (%v)", docid, code, msg, err)
			err = nil // wrote it to output already; not going to return it
		} else {
			status["rev"] = revid
		}
		result = append(result, status)
	}

	for _, item := range localDocs {
		doc := item.(map[string]interface{})
		for k, v := range doc {
			doc[k] = base.FixJSONNumbers(v)
		}
		var err error
		var revid string
		offset := len("_local/")
		docid, _ := doc["_id"].(string)
		idslug := docid[offset:]
		revid, err = h.db.PutSpecial("local", idslug, doc)
		status := db.Body{}
		status["id"] = docid
		if err != nil {
			code, msg := base.ErrorAsHTTPStatus(err)
			status["status"] = code
			status["error"] = base.CouchHTTPErrorName(code)
			status["reason"] = msg
			base.Logf("\tBulkDocs: Local Doc %q --> %d %s (%v)", docid, code, msg, err)
			err = nil
		} else {
			status["rev"] = revid
		}
		result = append(result, status)
	}

	h.writeJSONStatus(http.StatusCreated, result)
	return nil
}