Project

General

Profile

« Previous | Next » 

Revision 3321

Added by barteau over 17 years ago

Initial checkin. The "Client View FGDC Helper", to provide FGDC specific methods for client views. This is an API class for the clientview package.

View differences:

src/edu/ucsb/nceas/metacat/clientview/ClientFgdcHelper.java
1
/*
2
 * ClientFgdcHelper.java
3
 *
4
 * Created on June 25, 2007, 9:58 AM
5
 *
6
 * To change this template, choose Tools | Template Manager
7
 * and open the template in the editor.
8
 */
9

  
10
package edu.ucsb.nceas.metacat.clientview;
11

  
12
import com.oreilly.servlet.multipart.MultipartParser;
13
import edu.ucsb.nceas.metacat.client.MetacatException;
14
import edu.ucsb.nceas.utilities.XMLUtilities;
15
import java.io.BufferedReader;
16
import java.io.IOException;
17
import java.io.InputStream;
18
import java.io.Reader;
19
import java.io.StringReader;
20
import java.util.HashMap;
21
import java.util.Iterator;
22
import java.util.Properties;
23
import javax.xml.xpath.XPath;
24
import javax.xml.xpath.XPathConstants;
25
import javax.xml.xpath.XPathExpressionException;
26
import javax.xml.xpath.XPathFactory;
27
import org.w3c.dom.Document;
28
import org.w3c.dom.DocumentType;
29
import org.w3c.dom.Node;
30
import org.w3c.dom.NodeList;
31

  
32
/**
33
 *
34
 * @author barteau
35
 */
36
public abstract class ClientFgdcHelper {
37
    
38
    private static XPath                    xpath = XPathFactory.newInstance().newXPath();
39
    
40
    /**
41
     * Data Document ID location within an FGDC document.  XPath expression.
42
     */
43
    public static final String              FGDC_DATA_FILE_DOCID_XPATH = "/metadata/distinfo/stdorder/digform/digtopt/onlinopt/computer/networka/networkr";
44
    
45
    public static final String              PATH4ANCESTOR = FGDC_DATA_FILE_DOCID_XPATH + "[text()='%1$s']/ancestor::node()[name()='%2$s']";
46
    
47
    /**
48
     * Metadata Document ID location within an FGDC document.  XPath expression.
49
     */
50
    public static final String              FGDC_DOCID_XPATH = "/metadata/distinfo/resdesc";
51
    
52
    public static final String              XPATH_QUERY_TEMPLATE = FGDC_DOCID_XPATH + "[text()='%1$s']";
53
    
54
    /**
55
     * Identifies the FGDC DTD.
56
     */
57
    public static final String              FGDC_SYSTEM_ID = "http://www.fgdc.gov/metadata/fgdc-std-001-1998.dtd";
58
    
59
    /**
60
     * Handles a client's request to delete a document.
61
     * If its a data document, it removes the Doc Id from the FGDC metadata in the
62
     * Metacat database.  It determines what metadata Doc ID is including this Doc Id.
63
     * It then queries metacat for the parent FGDC document and removes the Doc Id from it, and
64
     * reloads the new version with a new revision number.
65
     * If its a metadata document, it deletes any related data documents, then it
66
     * deletes the metadata.  In either instance, it sets the server feedback in
67
     * the session ("updateFeedback").
68
     * @param request HttpServletRequest which contains docId parameter.
69
     */
70
    public static void clientDeleteRequest(ClientView clientViewBean, ClientViewHelper clientViewHelper) {
71
        String                      result = null, docId, subDocId, parentDocId, revisedDocId;
72
        NodeList                    nodeLst;
73
        final String                SUB_DOCS_PATH = FGDC_DATA_FILE_DOCID_XPATH + "/text()";
74
        Node                        node;
75
        Document                    resultSetDoc;
76
        
77
        docId = clientViewBean.getDocId();
78
        try {
79
            //*** First, determine what metadata file is including this file (if any).
80
            resultSetDoc = clientViewHelper.query(FGDC_DATA_FILE_DOCID_XPATH, docId, null);
81
            parentDocId = xpath.evaluate("/resultset/document/docid", resultSetDoc.getDocumentElement());
82
            if (parentDocId != null && !parentDocId.equals("")) {
83
                clientViewHelper.setMetadataDoc(parentDocId);
84
                //*** Remove Doc Id from any parent metadata document.
85
                revisedDocId = removeDataDocIdFromFGDC(docId, parentDocId, clientViewHelper);
86
                clientViewBean.setDocId(revisedDocId);
87
            } else {
88
                clientViewHelper.setMetadataDoc(docId);
89
                //*** This is a metadata document, so remove all of the sub-docId's.
90
                nodeLst = (NodeList) xpath.evaluate(SUB_DOCS_PATH, clientViewHelper.getMetadataDoc().getDocumentElement(), XPathConstants.NODESET);
91
                for(int i = 0; i < nodeLst.getLength(); i++) {
92
                    node = nodeLst.item(i);
93
                    subDocId = node.getNodeValue();
94
                    
95
                    //*** Remove the sub-document.
96
                    try {
97
                        clientViewHelper.getMetacatClient().delete(subDocId);
98
                    } catch (MetacatException ex) {
99
                        ex.printStackTrace();
100
                    }
101
                }
102
            }
103
            //*** Remove the document.
104
            result = clientViewHelper.getMetacatClient().delete(docId);
105
            
106
            //*** Save the server feedback in the session, to be used by the view.
107
            clientViewBean.setMessage(ClientView.DELETE_MESSAGE, result);
108
        } catch (Exception ex) {
109
            ex.printStackTrace();
110
        }
111
    }
112
    
113
    private static String removeDataDocIdFromFGDC(String docId, String parentDocId, ClientViewHelper clientViewHelper) throws Exception {
114
        String                          pathToDigform, revision = "", xPathQuery;
115
        Document                        doc;
116
        InputStream                     response;
117
        BufferedReader                  buffy;
118
        Properties                      prop;
119
        Node                            node;
120
        NodeList                        nodeLst;
121
        Reader                          reader;
122
        
123
        //*** Get the metadata document and remove the digform branch.
124
        doc = clientViewHelper.getMetadataDoc();
125
        if (doc != null) {
126
            pathToDigform = String.format(PATH4ANCESTOR, docId, "digform");
127
            node = (Node) xpath.evaluate(pathToDigform, doc.getDocumentElement(), XPathConstants.NODE);
128
            node.getParentNode().removeChild(node);
129
            xPathQuery = String.format(XPATH_QUERY_TEMPLATE, docId);
130
            revision = clientViewHelper.nextVersion(parentDocId, xPathQuery);
131
            reader = XMLUtilities.getDOMTreeAsReader(doc.getDocumentElement(), false);
132
            clientViewHelper.getMetacatClient().update(revision, reader, null);
133
        }
134
        return(revision);
135
    }
136
    
137
    public static boolean handlePackageUpload(String metaDocId, HashMap dataDocIDs, String contactName, Document metadataDoc) throws IOException {
138
        boolean                         result = true;
139
        Node                            newBranch, metaRootNode;
140
        
141
        //*** Store the User Name and Doc Id in the FGDC document.
142
        newBranch = getFGDCdisinfo(contactName, metaDocId, dataDocIDs);
143
        System.out.println("ClientFgdcHelper.handlePackageUpload: " + XMLUtilities.getDOMTreeAsString(newBranch));
144
        metaRootNode = addDistInfoToFGDC(newBranch, metadataDoc);
145
        return(result);
146
    }
147
    
148
    
149
    public static boolean isFGDC(Document metadataDoc) {
150
        boolean                     result = false;
151
        DocumentType                docType;
152
        String                      sysId;
153
        final String                FGDC_TEST_EXPRESSION = "/metadata/idinfo/citation/citeinfo/title";
154
        Node                        node = null;
155
        
156
        //*** First, try the rigid proper way of determining it.
157
        if (metadataDoc != null) {
158
            docType = metadataDoc.getDoctype();
159
            if (docType != null) {
160
                sysId = docType.getSystemId();
161
                if (sysId != null)
162
                    result = sysId.contains(FGDC_SYSTEM_ID);
163
            }
164
        }
165
        //*** It might not have a doc type line, so try another method.
166
        if (metadataDoc != null && !result) {
167
            try {
168
                node = (Node) xpath.evaluate(FGDC_TEST_EXPRESSION, metadataDoc.getDocumentElement(), XPathConstants.NODE);
169
            } catch (XPathExpressionException ex) {
170
                ex.printStackTrace();
171
            }
172
            result = (node != null);
173
        }
174
        return(result);
175
    }
176
    
177
    private static Node getFGDCdisinfo(String contactName, String resourceDescription, HashMap dataDocIDs) throws IOException {
178
        Node                        result = null, node, digformBranch, formname, stdorder;
179
        Document                    doc;
180
        Iterator                    iterIt;
181
        String                      key, value;
182
        
183
        //*** This is a valid/minimal FGDC "distinfo" branch.
184
        final String XML = "<distinfo>"
185
                + "    <distrib>"
186
                + "        <cntinfo>"
187
                + "            <cntperp>"
188
                + "                <cntper></cntper>"
189
                + "            </cntperp>"
190
                + "            <cntaddr>"
191
                + "                <addrtype></addrtype>"
192
                + "                <address></address>"
193
                + "                <city></city>"
194
                + "                <state></state>"
195
                + "                <postal></postal>"
196
                + "                <country></country>"
197
                + "            </cntaddr>"
198
                + "            <cntvoice></cntvoice>"
199
                + "        </cntinfo>"
200
                + "    </distrib>"
201
                + "    <resdesc></resdesc>"
202
                + "    <distliab></distliab>"
203
                + "    <stdorder>"
204
                + "        <digform>"
205
                + "            <digtinfo>"
206
                + "                <formname></formname>"
207
                + "            </digtinfo>"
208
                + "            <digtopt>"
209
                + "                <onlinopt>"
210
                + "                    <computer>"
211
                + "                        <networka>"
212
                + "                            <networkr></networkr>"
213
                + "                        </networka>"
214
                + "                    </computer>"
215
                + "                </onlinopt>"
216
                + "            </digtopt>"
217
                + "        </digform>"
218
                + "        <fees></fees>"
219
                + "    </stdorder>"
220
                + "</distinfo>";
221
        
222
        doc = XMLUtilities.getXMLReaderAsDOMDocument(new StringReader(XML));
223
        result = doc.getDocumentElement();
224
        try {
225
            //*** Set the Contact Person.
226
            node = (Node) xpath.evaluate("/distinfo/distrib/cntinfo/cntperp/cntper", result, XPathConstants.NODE);
227
            node.setTextContent(contactName);
228
            //*** Set the metadata Doc Id.
229
            node = (Node) xpath.evaluate("/distinfo/resdesc", result, XPathConstants.NODE);
230
            node.setTextContent(resourceDescription);
231
            
232
            //*** Loop thru the files, setting their format and Doc Id.
233
            stdorder = (Node) xpath.evaluate("/distinfo/stdorder", result, XPathConstants.NODE);
234
            digformBranch = (Node) xpath.evaluate("/distinfo/stdorder/digform", result, XPathConstants.NODE);
235
            iterIt = dataDocIDs.keySet().iterator();
236
            while(iterIt.hasNext()) {
237
                //*** Save the data file Doc ID (required).
238
                key = (String) iterIt.next();
239
                node = (Node) xpath.evaluate("digtopt/onlinopt/computer/networka/networkr", digformBranch, XPathConstants.NODE);
240
                node.setTextContent(key);
241
                //*** Save the data file format (optional).
242
                formname = (Node) xpath.evaluate("digtinfo/formname", digformBranch, XPathConstants.NODE);
243
                if ((value = (String) dataDocIDs.get(key)) != null && !value.equals("")) {
244
                    formname.setTextContent(value);
245
                } else {
246
                    //*** We did a deep clone of the branch, so clear prior contents.
247
                    formname.setTextContent("");
248
                }
249
                
250
                //*** Clone branch for next file.
251
                if (iterIt.hasNext()) {
252
                    digformBranch = digformBranch.cloneNode(true);
253
                    stdorder.appendChild(digformBranch);
254
                }
255
            }
256
        } catch (XPathExpressionException ex) {
257
            ex.printStackTrace();
258
        }
259
        return(result);
260
    }
261
    
262
    private static Node addDistInfoToFGDC(Node newBranch, Document metadataDoc) {
263
        Node                        result = null, node;
264
        
265
        if (newBranch != null) {
266
            result = metadataDoc.getDocumentElement();
267
            try {
268
                //*** Get a reference to the FGDC required "metainfo" node (only 1 allowed).
269
                node = (Node) xpath.evaluate("/metadata/metainfo", result, XPathConstants.NODE);
270
                if (node != null) {
271
                    newBranch = metadataDoc.importNode(newBranch, true);
272
                    //*** Add the new "distinfo" before it.
273
                    result.insertBefore(newBranch, node);
274
                }
275
            } catch (XPathExpressionException ex) {
276
                ex.printStackTrace();
277
            }
278
        }
279
        return(result);
280
    }
281
}
0 282

  

Also available in: Unified diff