With the help of various other posts I've put together C# source code that works. Hopefully this will help others out there.
public static bool UploadFile(string host, string directory, string filePathName, ICredentials credentials) {
Uri uri = null;
string fileName = Path.GetFileName(filePathName);
if (directory == null)
uri = new Uri(string.Format(@"ftp://{0}/", host));
else
uri = new Uri(string.Format(@"ftp://{0}/{1}/", host, directory));
try {
FtpRequestCreator creator = new FtpRequestCreator();
WebRequest.RegisterPrefix("ftp:", creator);
FtpWebRequest ftpWebRequest = (FtpWebRequest)WebRequest.Create(uri);
ftpWebRequest.Credentials = credentials;
// Getting the Request stream
Stream ftpRequestStream = ftpWebRequest.GetRequestStream();
StreamReader responseReader = new StreamReader(ftpRequestStream);
// Just ignore the result, but read it.
String responseString = responseReader.ReadToEnd();
// Open the input file. If the file does not exist, it's an error.
FileStream filestream = new FileStream(filePathName, FileMode.Open);
// Create the reader for the local file data.
BinaryReader fileReader = new BinaryReader(filestream);
// Opening the data connection, this must be done before we issue the command.
Stream ftpResponseStream = ftpWebRequest.GetResponse().GetResponseStream();
BinaryWriter dataWriter = new BinaryWriter(ftpResponseStream);
// Prepare to send commands to the server.
StreamWriter commandWriter = new StreamWriter(ftpRequestStream);
// Set transfer type to IMAGE (binary).
commandWriter.Write("TYPE I\r\n");
commandWriter.Flush();
// Reading the request output
responseReader = new StreamReader(ftpRequestStream);
responseString = responseReader.ReadToEnd();
// Write the command to the request stream.
String cmd = "stor " + fileName + "\r\n";
commandWriter.Write(cmd);
commandWriter.Flush(); // We MUST flush before we start reading from both response and request
// Reading the request output
responseString = responseReader.ReadToEnd();
// Allocate buffer for the data, which will be written in blocks.
int bufsize = 1024;
byte[] buf = new byte[bufsize];
int xcount;
while ((xcount = fileReader.Read(buf, 0, bufsize)) > 0) {
// Send next buffer over the data connection.
dataWriter.Write(buf, 0, xcount);
}
fileReader.Close();
filestream.Close();
dataWriter.Close();
responseReader.Close();
return true;
} catch (Exception ex) {
throw ex;
}
}