1 /*******************************************************************************
\r
2 * ============LICENSE_START====================================================
\r
4 * * ===========================================================================
\r
5 * * Copyright © 2017 AT&T Intellectual Property. All rights reserved.
\r
6 * * ===========================================================================
\r
7 * * Licensed under the Apache License, Version 2.0 (the "License");
\r
8 * * you may not use this file except in compliance with the License.
\r
9 * * You may obtain a copy of the License at
\r
11 * * http://www.apache.org/licenses/LICENSE-2.0
\r
13 * * Unless required by applicable law or agreed to in writing, software
\r
14 * * distributed under the License is distributed on an "AS IS" BASIS,
\r
15 * * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
\r
16 * * See the License for the specific language governing permissions and
\r
17 * * limitations under the License.
\r
18 * * ============LICENSE_END====================================================
\r
20 * * ECOMP is a trademark and service mark of AT&T Intellectual Property.
\r
22 ******************************************************************************/
\r
23 package org.onap.aaf.authz.local;
\r
25 import java.io.File;
\r
26 import java.io.FileNotFoundException;
\r
27 import java.io.IOException;
\r
28 import java.io.RandomAccessFile;
\r
29 import java.util.Iterator;
\r
31 import org.onap.aaf.authz.env.AuthzTrans;
\r
32 import org.onap.aaf.authz.local.DataFile.Token;
\r
33 import org.onap.aaf.authz.local.DataFile.Token.Field;
\r
35 import org.onap.aaf.inno.env.Env;
\r
36 import org.onap.aaf.inno.env.TimeTaken;
\r
38 public abstract class AbsData implements Iterable<String> {
\r
39 protected DataFile data;
\r
40 protected TextIndex ti;
\r
41 private File dataf,idxf,lockf;
\r
42 private String name;
\r
44 private int maxLineSize;
\r
45 private int fieldOffset;
\r
46 private int skipLines;
\r
48 public AbsData(File dataf,char sepChar, int maxLineSize, int fieldOffset) {
\r
49 File dir = dataf.getParentFile();
\r
50 int dot = dataf.getName().lastIndexOf('.');
\r
52 name = dataf.getName().substring(0,dot);
\r
56 this.delim = sepChar;
\r
57 this.maxLineSize = maxLineSize;
\r
58 this.fieldOffset = fieldOffset;
\r
59 idxf = new File(dir,name.concat(".idx"));
\r
60 lockf = new File(dir,name.concat(".lock"));
\r
63 data = new DataFile(dataf,"r");
\r
64 ti = new TextIndex(idxf);
\r
68 public void skipLines(int lines) {
\r
72 public String name() {
\r
76 public void open(AuthzTrans trans, long timeout) throws IOException {
\r
77 TimeTaken tt = trans.start("Open Data File", Env.SUB);
\r
78 boolean opened = false, first = true;
\r
80 if(!dataf.exists()) {
\r
81 throw new FileNotFoundException("Data File Missing:" + dataf.getCanonicalPath());
\r
83 long begin = System.currentTimeMillis();
\r
84 long end = begin+timeout;
\r
86 while((exists=lockf.exists()) && begin<end) {
\r
88 trans.warn().log("Waiting for",lockf.getCanonicalPath(),"to close");
\r
93 } catch (InterruptedException e) {
\r
96 begin = System.currentTimeMillis();
\r
99 throw new IOException(lockf.getCanonicalPath() + "exists. May not open Datafile");
\r
103 ensureIdxGood(trans);
\r
104 } catch (IOException e) {
\r
115 throw new IOException("DataFile pair for " + name + " was not able to be opened in " + timeout + "ms");
\r
119 private synchronized void ensureIdxGood(AuthzTrans trans) throws IOException {
\r
120 if(!idxf.exists() || idxf.length()==0 || dataf.lastModified()>idxf.lastModified()) {
\r
121 trans.warn().log(idxf.getCanonicalPath(),"is missing, empty or out of date, creating");
\r
122 RandomAccessFile raf = new RandomAccessFile(lockf, "rw");
\r
124 ti.create(trans, data, maxLineSize, delim, fieldOffset, skipLines);
\r
125 if(!idxf.exists() || (idxf.length()==0 && dataf.length()!=0)) {
\r
126 throw new IOException("Data Index File did not create correctly");
\r
135 public void close(AuthzTrans trans) throws IOException {
\r
140 public class Reuse {
\r
141 private Token tokenData;
\r
142 private Field fieldData;
\r
144 private Reuse(int size,char delim) {
\r
145 tokenData = data.new Token(size);
\r
146 fieldData = getTokenData().new Field(delim);
\r
149 public void reset() {
\r
150 getFieldData().reset();
\r
153 public void pos(int rec) {
\r
154 getFieldData().reset();
\r
155 getTokenData().pos(rec);
\r
158 public String next() {
\r
159 return getFieldData().next();
\r
162 public String at(int field) {
\r
163 return getFieldData().at(field);
\r
166 public String atToEnd(int field) {
\r
167 return getFieldData().atToEnd(field);
\r
170 public Field getFieldData() {
\r
174 public Token getTokenData() {
\r
180 public Reuse reuse() {
\r
181 return new Reuse(maxLineSize,delim);
\r
184 public Iter iterator() {
\r
188 public class Iter implements Iterator<String> {
\r
189 private Reuse reuse;
\r
190 private org.onap.aaf.authz.local.TextIndex.Iter tii;
\r
194 tii = ti.new Iter();
\r
198 public boolean hasNext() {
\r
199 return tii.hasNext();
\r
203 public String next() {
\r
205 int rec = tii.next();
\r
207 return reuse.at(0);
\r
211 public void remove() {
\r