-
Notifications
You must be signed in to change notification settings - Fork 207
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
File source improvements and change to event model (#601)
Refactored file source, added record_type and format configuration options for json and plaintext, support for both Event And String Signed-off-by: Taylor Gray <[email protected]>
- Loading branch information
1 parent
8dd106b
commit 515fa4d
Showing
13 changed files
with
486 additions
and
250 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
91 changes: 0 additions & 91 deletions
91
...repper-plugins/common/src/main/java/com/amazon/dataprepper/plugins/source/FileSource.java
This file was deleted.
Oops, something went wrong.
33 changes: 33 additions & 0 deletions
33
...r-plugins/common/src/main/java/com/amazon/dataprepper/plugins/source/file/FileFormat.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,33 @@ | ||
package com.amazon.dataprepper.plugins.source.file; | ||
|
||
import java.util.Arrays; | ||
import java.util.Map; | ||
import java.util.function.Function; | ||
import java.util.stream.Collectors; | ||
|
||
/** | ||
* An enumm to represent the file formats supported in Data Prepper's file source. | ||
* @since 1.2 | ||
*/ | ||
public enum FileFormat { | ||
|
||
PLAIN("plain"), | ||
JSON("json"); | ||
|
||
private static final Map<String, FileFormat> NAMES_MAP = Arrays.stream(FileFormat.values()) | ||
.collect(Collectors.toMap(FileFormat::toString, Function.identity())); | ||
|
||
private final String name; | ||
|
||
FileFormat(final String name) { | ||
this.name = name; | ||
} | ||
|
||
public String toString() { | ||
return this.name; | ||
} | ||
|
||
public static FileFormat getByName(final String name) { | ||
return NAMES_MAP.get(name.toLowerCase()); | ||
} | ||
} |
121 changes: 121 additions & 0 deletions
121
...r-plugins/common/src/main/java/com/amazon/dataprepper/plugins/source/file/FileSource.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,121 @@ | ||
/* | ||
* SPDX-License-Identifier: Apache-2.0 | ||
* | ||
* The OpenSearch Contributors require contributions made to | ||
* this file be licensed under the Apache-2.0 license or a | ||
* compatible open source license. | ||
* | ||
* Modifications Copyright OpenSearch Contributors. See | ||
* GitHub history for details. | ||
*/ | ||
|
||
package com.amazon.dataprepper.plugins.source.file; | ||
|
||
import com.amazon.dataprepper.metrics.PluginMetrics; | ||
import com.amazon.dataprepper.model.annotations.DataPrepperPlugin; | ||
import com.amazon.dataprepper.model.annotations.DataPrepperPluginConstructor; | ||
import com.amazon.dataprepper.model.buffer.Buffer; | ||
import com.amazon.dataprepper.model.event.JacksonEvent; | ||
import com.amazon.dataprepper.model.plugin.PluginFactory; | ||
import com.amazon.dataprepper.model.record.Record; | ||
import com.amazon.dataprepper.model.source.Source; | ||
import com.fasterxml.jackson.core.JsonProcessingException; | ||
import com.fasterxml.jackson.core.type.TypeReference; | ||
import com.fasterxml.jackson.databind.ObjectMapper; | ||
import org.slf4j.Logger; | ||
import org.slf4j.LoggerFactory; | ||
|
||
import java.io.BufferedReader; | ||
import java.io.IOException; | ||
import java.nio.charset.StandardCharsets; | ||
import java.nio.file.Files; | ||
import java.nio.file.Paths; | ||
import java.util.HashMap; | ||
import java.util.Map; | ||
import java.util.concurrent.TimeoutException; | ||
|
||
import static com.google.common.base.Preconditions.checkNotNull; | ||
import static java.lang.String.format; | ||
|
||
@DataPrepperPlugin(name = "file", pluginType = Source.class, pluginConfigurationType = FileSourceConfig.class) | ||
public class FileSource implements Source<Record<Object>> { | ||
|
||
static final String MESSAGE_KEY = "message"; | ||
private static final Logger LOG = LoggerFactory.getLogger(FileSource.class); | ||
private static final TypeReference<Map<String, Object>> MAP_TYPE_REFERENCE = new TypeReference<Map<String, Object>>() {}; | ||
|
||
private static final ObjectMapper OBJECT_MAPPER = new ObjectMapper(); | ||
private final FileSourceConfig fileSourceConfig; | ||
|
||
private boolean isStopRequested; | ||
private final int writeTimeout; | ||
|
||
@DataPrepperPluginConstructor | ||
public FileSource(final FileSourceConfig fileSourceConfig, final PluginMetrics pluginMetrics, final PluginFactory pluginFactory) { | ||
fileSourceConfig.validate(); | ||
this.fileSourceConfig = fileSourceConfig; | ||
this.isStopRequested = false; | ||
this.writeTimeout = FileSourceConfig.DEFAULT_TIMEOUT; | ||
} | ||
|
||
|
||
@Override | ||
public void start(final Buffer<Record<Object>> buffer) { | ||
checkNotNull(buffer, "Buffer cannot be null for file source to start"); | ||
try (BufferedReader reader = Files.newBufferedReader(Paths.get(fileSourceConfig.getFilePathToRead()), StandardCharsets.UTF_8)) { | ||
String line; | ||
while ((line = reader.readLine()) != null && !isStopRequested) { | ||
writeLineAsEventOrString(line, buffer); | ||
} | ||
} catch (IOException | TimeoutException | IllegalArgumentException ex) { | ||
LOG.error("Error processing the input file path [{}]", fileSourceConfig.getFilePathToRead(), ex); | ||
throw new RuntimeException(format("Error processing the input file %s", | ||
fileSourceConfig.getFilePathToRead()), ex); | ||
} | ||
} | ||
|
||
@Override | ||
public void stop() { | ||
isStopRequested = true; | ||
} | ||
|
||
private Record<Object> getEventRecordFromLine(final String line) { | ||
Map<String, Object> structuredLine = new HashMap<>(); | ||
|
||
switch(fileSourceConfig.getFormat()) { | ||
case JSON: | ||
structuredLine = parseJson(line); | ||
break; | ||
case PLAIN: | ||
structuredLine.put(MESSAGE_KEY, line); | ||
break; | ||
} | ||
|
||
return new Record<>(JacksonEvent | ||
.builder() | ||
.withEventType(fileSourceConfig.getRecordType()) | ||
.withData(structuredLine) | ||
.build()); | ||
} | ||
|
||
private Map<String, Object> parseJson(final String jsonString) { | ||
try { | ||
return OBJECT_MAPPER.readValue(jsonString, MAP_TYPE_REFERENCE); | ||
} catch (JsonProcessingException e) { | ||
LOG.error("Unable to parse json data [{}], assuming plain text", jsonString, e); | ||
final Map<String, Object> plainMap = new HashMap<>(); | ||
plainMap.put(MESSAGE_KEY, jsonString); | ||
return plainMap; | ||
} | ||
} | ||
|
||
// Temporary function to support both trace and log ingestion pipelines. | ||
// TODO: This function should be removed with the completion of: https://github.com/opensearch-project/data-prepper/issues/546 | ||
private void writeLineAsEventOrString(final String line, final Buffer<Record<Object>> buffer) throws TimeoutException, IllegalArgumentException { | ||
if (fileSourceConfig.getRecordType().equals(FileSourceConfig.EVENT_TYPE)) { | ||
buffer.write(getEventRecordFromLine(line), writeTimeout); | ||
} else if (fileSourceConfig.getRecordType().equals(FileSourceConfig.DEFAULT_TYPE)) { | ||
buffer.write(new Record<>(line), writeTimeout); | ||
} | ||
} | ||
} |
46 changes: 46 additions & 0 deletions
46
...ins/common/src/main/java/com/amazon/dataprepper/plugins/source/file/FileSourceConfig.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,46 @@ | ||
package com.amazon.dataprepper.plugins.source.file; | ||
|
||
import com.fasterxml.jackson.annotation.JsonIgnore; | ||
import com.fasterxml.jackson.annotation.JsonProperty; | ||
import com.google.common.base.Preconditions; | ||
|
||
import java.util.Objects; | ||
|
||
public class FileSourceConfig { | ||
static final String ATTRIBUTE_PATH = "path"; | ||
static final String ATTRIBUTE_TYPE = "record_type"; | ||
static final String ATTRIBUTE_FORMAT = "format"; | ||
static final int DEFAULT_TIMEOUT = 5_000; | ||
static final String DEFAULT_TYPE = "string"; | ||
static final String DEFAULT_FORMAT = "plain"; | ||
static final String EVENT_TYPE = "event"; | ||
|
||
|
||
@JsonProperty(ATTRIBUTE_PATH) | ||
private String filePathToRead; | ||
|
||
@JsonProperty(ATTRIBUTE_FORMAT) | ||
private String format = DEFAULT_FORMAT; | ||
|
||
@JsonProperty(ATTRIBUTE_TYPE) | ||
private String recordType = DEFAULT_TYPE; | ||
|
||
public String getFilePathToRead() { | ||
return filePathToRead; | ||
} | ||
|
||
@JsonIgnore | ||
public FileFormat getFormat() { | ||
return FileFormat.getByName(format); | ||
} | ||
|
||
public String getRecordType() { | ||
return recordType; | ||
} | ||
|
||
void validate() { | ||
Objects.requireNonNull(filePathToRead, "File path is required"); | ||
Preconditions.checkArgument(recordType.equals(EVENT_TYPE) || recordType.equals(DEFAULT_TYPE), "Invalid type: must be either [event] or [string]"); | ||
Preconditions.checkArgument(format.equals(DEFAULT_FORMAT) || format.equals("json"), "Invalid file format. Options are [json] and [plain]"); | ||
} | ||
} |
Oops, something went wrong.