1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 package org.apache.hadoop.hbase.rest;
21
22 import java.io.ByteArrayInputStream;
23 import java.io.IOException;
24 import java.io.StringWriter;
25 import java.util.ArrayList;
26 import java.util.Collection;
27 import java.util.List;
28
29 import javax.xml.bind.JAXBContext;
30 import javax.xml.bind.JAXBException;
31
32 import org.apache.http.Header;
33 import org.apache.http.message.BasicHeader;
34
35 import org.apache.hadoop.conf.Configuration;
36 import org.apache.hadoop.hbase.HBaseTestingUtility;
37 import org.apache.hadoop.hbase.testclassification.MediumTests;
38 import org.apache.hadoop.hbase.TableName;
39 import org.apache.hadoop.hbase.client.Admin;
40 import org.apache.hadoop.hbase.rest.client.Client;
41 import org.apache.hadoop.hbase.rest.client.Cluster;
42 import org.apache.hadoop.hbase.rest.client.Response;
43 import org.apache.hadoop.hbase.rest.model.ColumnSchemaModel;
44 import org.apache.hadoop.hbase.rest.model.TableSchemaModel;
45 import org.apache.hadoop.hbase.rest.model.TestTableSchemaModel;
46 import org.apache.hadoop.hbase.util.Bytes;
47
48 import static org.junit.Assert.*;
49
50 import org.junit.AfterClass;
51 import org.junit.BeforeClass;
52 import org.junit.Test;
53 import org.junit.experimental.categories.Category;
54 import org.junit.runner.RunWith;
55 import org.junit.runners.Parameterized;
56
57 @Category(MediumTests.class)
58 @RunWith(Parameterized.class)
59 public class TestSchemaResource {
60 private static String TABLE1 = "TestSchemaResource1";
61 private static String TABLE2 = "TestSchemaResource2";
62
63 private static final HBaseTestingUtility TEST_UTIL = new HBaseTestingUtility();
64 private static final HBaseRESTTestingUtility REST_TEST_UTIL =
65 new HBaseRESTTestingUtility();
66 private static Client client;
67 private static JAXBContext context;
68 private static Configuration conf;
69 private static TestTableSchemaModel testTableSchemaModel;
70 private static Header extraHdr = null;
71
72 private static boolean csrfEnabled = true;
73
74 @Parameterized.Parameters
75 public static Collection<Object[]> data() {
76 List<Object[]> params = new ArrayList<Object[]>();
77 params.add(new Object[] {Boolean.TRUE});
78 params.add(new Object[] {Boolean.FALSE});
79 return params;
80 }
81
82 public TestSchemaResource(Boolean csrf) {
83 csrfEnabled = csrf;
84 }
85
86 @BeforeClass
87 public static void setUpBeforeClass() throws Exception {
88 conf = TEST_UTIL.getConfiguration();
89 conf.setBoolean(RESTServer.REST_CSRF_ENABLED_KEY, csrfEnabled);
90 extraHdr = new BasicHeader(RESTServer.REST_CSRF_CUSTOM_HEADER_DEFAULT, "");
91 TEST_UTIL.startMiniCluster();
92 REST_TEST_UTIL.startServletContainer(conf);
93 client = new Client(new Cluster().add("localhost",
94 REST_TEST_UTIL.getServletPort()));
95 testTableSchemaModel = new TestTableSchemaModel();
96 context = JAXBContext.newInstance(
97 ColumnSchemaModel.class,
98 TableSchemaModel.class);
99 }
100
101 @AfterClass
102 public static void tearDownAfterClass() throws Exception {
103 REST_TEST_UTIL.shutdownServletContainer();
104 TEST_UTIL.shutdownMiniCluster();
105 }
106
107 private static byte[] toXML(TableSchemaModel model) throws JAXBException {
108 StringWriter writer = new StringWriter();
109 context.createMarshaller().marshal(model, writer);
110 return Bytes.toBytes(writer.toString());
111 }
112
113 private static TableSchemaModel fromXML(byte[] content)
114 throws JAXBException {
115 return (TableSchemaModel) context.createUnmarshaller()
116 .unmarshal(new ByteArrayInputStream(content));
117 }
118
119 @Test
120 public void testTableCreateAndDeleteXML() throws IOException, JAXBException {
121 String schemaPath = "/" + TABLE1 + "/schema";
122 TableSchemaModel model;
123 Response response;
124
125 Admin admin = TEST_UTIL.getHBaseAdmin();
126 assertFalse(admin.tableExists(TableName.valueOf(TABLE1)));
127
128
129 model = testTableSchemaModel.buildTestModel(TABLE1);
130 testTableSchemaModel.checkModel(model, TABLE1);
131 if (csrfEnabled) {
132
133 response = client.put(schemaPath, Constants.MIMETYPE_XML, toXML(model));
134 assertEquals(response.getCode(), 400);
135 }
136
137 response = client.put(schemaPath, Constants.MIMETYPE_XML, toXML(model), extraHdr);
138 assertEquals(response.getCode(), 201);
139
140
141 conf.set("hbase.rest.readonly", "true");
142 response = client.put(schemaPath, Constants.MIMETYPE_XML, toXML(model), extraHdr);
143 assertEquals(response.getCode(), 403);
144
145
146 response = client.get(schemaPath, Constants.MIMETYPE_XML);
147 assertEquals(response.getCode(), 200);
148 assertEquals(Constants.MIMETYPE_XML, response.getHeader("content-type"));
149 model = fromXML(response.getBody());
150 testTableSchemaModel.checkModel(model, TABLE1);
151
152
153 response = client.get(schemaPath, Constants.MIMETYPE_JSON);
154 assertEquals(response.getCode(), 200);
155 assertEquals(Constants.MIMETYPE_JSON, response.getHeader("content-type"));
156 model = testTableSchemaModel.fromJSON(Bytes.toString(response.getBody()));
157 testTableSchemaModel.checkModel(model, TABLE1);
158
159 if (csrfEnabled) {
160
161 response = client.delete(schemaPath);
162 assertEquals(400, response.getCode());
163 }
164
165
166 response = client.delete(schemaPath, extraHdr);
167 assertEquals(response.getCode(), 403);
168
169
170 conf.set("hbase.rest.readonly", "false");
171
172
173 response = client.delete(schemaPath, extraHdr);
174 assertEquals(response.getCode(), 200);
175 assertFalse(admin.tableExists(TableName.valueOf(TABLE1)));
176 }
177
178 @Test
179 public void testTableCreateAndDeletePB() throws IOException, JAXBException {
180 String schemaPath = "/" + TABLE2 + "/schema";
181 TableSchemaModel model;
182 Response response;
183
184 Admin admin = TEST_UTIL.getHBaseAdmin();
185 assertFalse(admin.tableExists(TableName.valueOf(TABLE2)));
186
187
188 model = testTableSchemaModel.buildTestModel(TABLE2);
189 testTableSchemaModel.checkModel(model, TABLE2);
190
191 if (csrfEnabled) {
192
193 response = client.put(schemaPath, Constants.MIMETYPE_PROTOBUF, model.createProtobufOutput());
194 assertEquals(response.getCode(), 400);
195 }
196 response = client.put(schemaPath, Constants.MIMETYPE_PROTOBUF,
197 model.createProtobufOutput(), extraHdr);
198 assertEquals(response.getCode(), 201);
199
200
201 conf.set("hbase.rest.readonly", "true");
202 response = client.put(schemaPath, Constants.MIMETYPE_PROTOBUF,
203 model.createProtobufOutput(), extraHdr);
204 assertNotNull(extraHdr);
205 assertEquals(response.getCode(), 403);
206
207
208 response = client.get(schemaPath, Constants.MIMETYPE_PROTOBUF);
209 assertEquals(response.getCode(), 200);
210 assertEquals(Constants.MIMETYPE_PROTOBUF, response.getHeader("content-type"));
211 model = new TableSchemaModel();
212 model.getObjectFromMessage(response.getBody());
213 testTableSchemaModel.checkModel(model, TABLE2);
214
215
216 response = client.get(schemaPath, Constants.MIMETYPE_PROTOBUF_IETF);
217 assertEquals(response.getCode(), 200);
218 assertEquals(Constants.MIMETYPE_PROTOBUF_IETF, response.getHeader("content-type"));
219 model = new TableSchemaModel();
220 model.getObjectFromMessage(response.getBody());
221 testTableSchemaModel.checkModel(model, TABLE2);
222
223 if (csrfEnabled) {
224
225 response = client.delete(schemaPath);
226 assertEquals(400, response.getCode());
227 }
228
229
230 response = client.delete(schemaPath, extraHdr);
231 assertEquals(response.getCode(), 403);
232
233
234 conf.set("hbase.rest.readonly", "false");
235
236
237 response = client.delete(schemaPath, extraHdr);
238 assertEquals(response.getCode(), 200);
239 assertFalse(admin.tableExists(TableName.valueOf(TABLE2)));
240 }
241
242 }
243