All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.diirt.datasource.file.FileChannelHandler Maven / Gradle / Ivy

There is a newer version: 3.1.7
Show newest version
/**
 * Copyright (C) 2010-14 diirt developers. See COPYRIGHT.TXT
 * All rights reserved. Use is subject to license terms. See LICENSE.TXT
 */
package org.diirt.datasource.file;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.OutputStream;

import org.diirt.datasource.ChannelWriteCallback;
import org.diirt.datasource.MultiplexedChannelHandler;
import org.diirt.vtype.VType;
import org.diirt.vtype.ValueFactory;

/**
 * Implementation for channels of a {@link LocalDataSource}.
 *
 * @author carcassi
 */
class FileChannelHandler extends MultiplexedChannelHandler {
    
    private final File file;
    private final FileDataSource dataSource;
    private final Runnable updateTask = new Runnable() {

        @Override
        public void run() {
            update();
        }
    };
        
    private final FileFormat format;

    FileChannelHandler(FileDataSource dataSource, String channelName, File file, FileFormat format) {
        super(channelName);
        this.file = file;
        this.dataSource = dataSource;
        this.format = format;
    }
    
    @Override
    public void connect() {
        processConnection(file);
        update();
        dataSource.getFileWatchService().addWatcher(file, updateTask);
    }
    
    private void update() {
        try {
            Object value = readValueFromFile(file);
            processMessage(value);
        } catch (Exception ex) {
            reportExceptionToAllReadersAndWriters(ex);
        }
    }
    
    protected Object readValueFromFile(File file) {
        try (FileInputStream in = new FileInputStream(file)) {
            return format.readValue(in);
        } catch (Exception e) {
            reportExceptionToAllReadersAndWriters(e);
        }
        return null;
    }

    @Override
    public void disconnect() {
        dataSource.getFileWatchService().removeWatcher(file, updateTask);
        processConnection(null);
    }

    @Override
    protected boolean isConnected(File payload) {
        return payload != null && payload.exists() && payload.isFile();
    }

    @Override
    protected boolean isWriteConnected(File payload) {
        return isConnected(payload) && format.isWriteSupported();
    }

    @Override
    protected void write(Object newValue, ChannelWriteCallback callback) {
        if (file == null) {
            callback.channelWritten(new RuntimeException("Channel is closed"));
        }
        
        if (format == null || !format.isWriteSupported()) {
            callback.channelWritten(new RuntimeException("Format does not support write"));
        }
        
        // If the new value is not a VType, try to convert it using
        // the standard conversions
        if (!(newValue instanceof VType)) {
            Object converted = ValueFactory.toVType(newValue);
            if (converted != null) {
                newValue = converted;
            }
        }
        
        try (OutputStream out = new FileOutputStream(file)) {
            format.writeValue(newValue, out);
            callback.channelWritten(null);
        } catch (Exception ex) {
            callback.channelWritten(ex);
        }
    }

}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy