‘We Were Trapped With You’: The Subway Shooter Faces His Victims
ByNoah Hurowitz,
a freelance journalist and author based in New York
Wounded passengers on the platform of the 36th Street station in Sunset Park, moments after a gunman shot ten people aboard their train in April 2022.
Photo: Raymond Chiodini/@pretzal_maschine
Perched in a corner seat on the northbound N train, dressed in a hard hat and a reflective neon vest that lent him the guise of an MTA worker, Frank James cast a helpful figure as he urged multiple people to avoid the seat next to him in which water appeared to be pooling, seemingly saving his fellow straphangers from an unpleasant start to their day.
Then, with a muffled pop, the helpful man in the corner of the train in Sunset Park revealed himself as a gunman firing a barrage of shots as the train sped through Brooklyn in April 2022.On Thursday, James appeared in Brooklyn federal court for sentencing, where he was confronted by three of his victims and listened to written testimony from two others whose statements were delivered by prosecutors.
“I don’t know if you remember, but we greeted each other that day,” said one tall young man with spiky black hair, identified in court only by his initials, B.K., addressing James directly. “We were in a community that day on that train car.”
Another passenger, identified in court by her initials C.T., remembered going for the empty seat next to James before he waved her away.
“I looked him in the eye and I thanked him,” recalled C.T., whose written testimony was delivered by prosecutors.
Moments later, James tossed a smoke grenade to the floor, and all hell broke loose.
“The train car quickly filled with smoke and everyone began to panic as we all rushed to try and exit the train,” C.T. wrote. “I prayed that God would protect us. I prayed that this would end soon. I prayed that the train would start moving.”
B.K., pinned under a crush of people huddled at the back of the train, felt his lungs constricting as he choked on acrid smoke spewing from the device James had set off.
“I realized what was happening. I realized we were trapped with you,” B.K. told James. “There was nothing stopping you from working your way methodically through the car, hurting us or killing us.”
Another passenger that day, Fitim Gjeloshi, told James he forgave him and hoped he got the help he needed. Then he broke down in tears, muttering, “I’m sorry, I can’t do this,” before rushing from the courtroom.
In written testimony, Furong Hu, a college student, told James how his life was derailed by the attack. Hu was shot five times, and said he is still unable to run or even use stairs. Now depressed and anxious, he had withdrawn socially and felt abandoned by his friends and girlfriend.
“I so desperately want my life back,” Hu wrote.
Speaking in court, a man identified as L.C. described self-medicating with alcohol and marijuana in the wake of the attack, a downward spiral that led to a stint in rehab.
“Your mother would have been ashamed of you,” L.C. said, his voice rising with anger. “I found help. Why couldn’t you find help, Mr. James?”
Seated at the table of his defense team in court on Thursday dressed in olive-drab prison clothes, James stared straight ahead as his victims addressed him, never once looking in their direction. Nor did he react when Judge William Kuntz sentenced him to ten concurrent life sentences — one for each person he shot — plus ten years’ imprisonment for discharging a firearm.
In a rambling speech that quoted Harriet Beecher Stowe, Frederick Douglass, and Jay-Z, James referenced decades-old grudges against former colleagues and social-services caseworkers who he claimed had it out for him, and at one point compared himself to Jordan Neely, the young Black man choked to death on the subway earlier this year. While expressing remorse at the harm he caused, and repeatedly referring to the shooting as a “cowardly act of senseless violence,” James ultimately cast his actions as a cry for help.
“It is my prayer that nobody copies my actions simply because they have no way to bring about change,” he said.
In a series of documents filed ahead of the sentencing hearing, experts hired by James’s attorneys detailed a harrowing life of isolation, paranoia, and untreated mental illness. Even before his birth, his family was marked by tragedy: In 1954, his brother Phillip fell to his death after being left unattended at home, and his mother was diagnosed with lung cancer a year later. When James was born in 1959, his attorneys said he quickly became a target of his father’s rage and suffered repeated physical abuse.
James was only 5 years old when his mother died, and he was in his teens when symptoms of mental illness began to become apparent, including paranoid delusions and hallucinations that prompted his first psychiatric hospitalization. These patterns of paranoia and alienation would follow James for decades, and apart from periodic hospitalizations or contacts with social workers, his social isolation and frequent moves to cities like Milwaukee and Philadelphia left him essentially untreated. Over the years, he self-medicated with alcohol, and over time he began to turn his inner rage outward at the world.
Finally, James “snapped,” according to Mia Eisner-Grynberg, an attorney with the Federal Defenders of New York who represented James.
“After decades of persistently seeking, but never receiving, appropriate mental-health care, Mr. James wrought unspeakable horror on innocent subway riders, each entirely blameless for his struggles,” Eisner-Grynberg wrote to the court.
But prosecutors disputed the shooting as some manifestation of James having suddenly lost it. In a sentencing memo, they listed numerous indications that James had planned the attack for months, even years ahead of that bloody morning in April. He had purchased the same brand of smoke grenades used in the attack in 2017 and 2019, and later that year he purchased ammunition identical to the bullets fired on the train; he had purchased the hard hat he wore as part of his disguise in 2021. And in the months leading up to the attack, he made multiple internet searches about buying a gun in Ohio and the location of N-train stops in Brooklyn.
And in his online rantings, James made numerous references to a potential attack, including one video posted on August 5, 2019, two and a half years prior to the shootings. At “the very least it’s going to be very interesting,” he said. “Let me say that. It’s going to be very interesting what happens in New York with me.”
And on the day of the attack, his planning — including shooing other passengers away from the seat next to him — was brutally effective in creating what prosecutors called a “kill funnel” that allowed James a clear line of sight to mow down his victims. Standing at one end of the train car, James fired a total of 32 times as his victims cowered at the other end of the car, suffocated and blinded by the smoke. He stopped shooting when his handgun jammed, despite having two additional magazines holding 18 rounds each.
“I sat there for a few moments as the smoke began to clear and assess what was around me. The floor was covered in blood,” C.T. recalled. “As I exited the train, I noticed several people laying down on the ground that had been injured. I put my hands on my knees, took a few deep breaths, and then looked to see who needed the most help.”
The platform at 36th Street was smeared with blood as gunshot victims tumbled out of the train. Ten people were wounded by gunshots, including five who required emergency surgery, prosecutors said. Amid the chaos, James slipped away, and as the city hunkered down in fear and confusion, he embarked on a tour of New York, periodically swapping out face masks and changing items of clothing to avoid detection. Throughout the day, he pulled up news stories about the shooting on a burner phone; he also watched a chase sequence from a James Bond film ten times. Eventually, he took a PATH train to Newark, where he spent the night.
That evening, after discovering a slew of evidence at the scene tying him to the attack, authorities publicly identified James as a person of interest. Early the next afternoon, James called the Crime Stoppers tip line to report himself, and a short while later police took him into custody at the corner of St. Marks and First Avenue in the East Village.
He was charged with ten counts of committing a terrorist act — one for each of the victims he shot — and one count of discharging a firearm in furtherance of the act. On January 3, he pleaded guilty to all 11 charges.
The attack spawned at least two civil cases, one against the MTA for alleged lapses in security — including nonfunctioning security cameras at 36th Street and 25th Street — and another against Glock, the manufacturer of the handgun James used to shoot his victims. Lawyers for the victims in both civil cases declined to comment on the sentencing.
By submitting your email, you agree to our
Terms and Privacy Notice
and to receive email correspondence from us. This site is protected by reCAPTCHA and the Google
Privacy Policy and
Terms of Service apply.
or
Already a subscriber?
What is your email?
This email will be used to sign into all New York sites. By submitting your email, you agree to our Terms and Privacy Policy and to receive email correspondence from us.
Password must be at least 8 characters and contain:
Lower case letters (a-z)
Upper case letters (A-Z)
Numbers (0-9)
Special Characters (!@#$%^&*)
This password will be used to sign into all New York sites. By submitting your email, you agree to our Terms and Privacy Policy and to receive email correspondence from us.
You’re in!
As part of your account, you’ll receive occasional updates and offers from New York, which you can opt out of anytime.
or
Already a subscriber?
What is your email?
This email will be used to sign into all New York sites. By submitting your email, you agree to our Terms and Privacy Policy and to receive email correspondence from us.
Password must be at least 8 characters and contain:
Lower case letters (a-z)
Upper case letters (A-Z)
Numbers (0-9)
Special Characters (!@#$%^&*)
This password will be used to sign into all New York sites. By submitting your email, you agree to our Terms and Privacy Policy and to receive email correspondence from us.
You’re in!
As part of your account, you’ll receive occasional updates and offers from New York, which you can opt out of anytime.
Already a subscriber?
Already a subscriber?
`;
// integrate Sub(x) scripts and elements
if (hostname !== 'subs.nymag.com') { // do not integrate on this subdomain
document.head.appendChild(trackingScript);
document.body.insertAdjacentHTML('beforeend', subXAnimationElements);
}
There was an error processing the request. Please try again later."}).catch(e=>console.error("Error verifying email: ",e)))(r.querySelector(".content"),o.bannerCTAVerification)})):(l.remove(),s.remove()),o.dismissable||n.remove(),o.useAlertIcon||a.remove(),r.classList.add("show"),n.addEventListener("click",()=>{u(),r.classList.remove("show")})}else r.remove()}});
}, {"3":3,"6":6,"17":17,"35":35,"40":40}];
window.modules["global-nav.client"] = [function(require,module,exports){"use strict";const dom=require(4),auth=require(17),signInButton=dom.find(".user-signin"),signOutButton=dom.find(".user-signout"),globalNav=dom.find('[class^="global-nav"]'),body=dom.find("body"),dropdownItems=dom.findAll(".dropdown-wrap"),gtm=require(3),appendLandingPageParams=require(135),pageUri=require(124).getPageUri(),subscriptionPromoLinks=dom.findAll(".persist-params"),searchString=window.location.search||"";function closeDropdowns(e){let n=globalNav.querySelectorAll(".dropdown.open");dropdownItems.forEach(function(t){let i=t.querySelector(".dropdown");!n||t.contains(e.target)&&27!==e.keyCode||i.classList.remove("open")})}function gtmSendReport(e,n,t){let i={eventCategory:"ecommerce",eventAction:"componentClick",brand:e,dimension23:"global-nav",list:pageUri,pageZone:"header",variant:"nav-link"};"global-nav-link"===t&&(i.eventLabel=n.href),gtm.reportNow(i)}function updateElementTargetUrlsIfQueryStrings(e){if(searchString){const n=new URLSearchParams(searchString);let t=e.href;if(t.includes("?")){const i=t.split("?"),o=new URLSearchParams(i[1]);for(let e of n.entries())o.set(e[0],e[1]);t=`${i[0]}?${o.toString()}`,e.href=t}else e.href=`${t}?${n.toString()}`}}function init(e){const n=e.querySelectorAll(".to-landing-page");window.addEventListener("auth:init",()=>{signInButton.addEventListener("click",function(e){e.preventDefault(),auth.showEmbeddedLoginFlow("top navigation")}),signOutButton.addEventListener("click",function(e){e.preventDefault(),gtmSendReport("Sign Out",e.target,"user-info-link"),auth.logout()}),auth.isAuthenticated()&&e.classList.add("signed-in"),(auth.isSubscriber()||auth.isMobileAppRequest())&&e.classList.add("subscribed"),e.querySelectorAll(".user-link").forEach(e=>{e.classList.add("active")}),subscriptionPromoLinks.forEach(e=>{updateElementTargetUrlsIfQueryStrings(e)}),appendLandingPageParams(n)})}dropdownItems.forEach(function(e){e.addEventListener("click",function(){e.querySelector(".dropdown").classList.toggle("open")})}),body.addEventListener("click",closeDropdowns),document.addEventListener("keydown",closeDropdowns),globalNav.addEventListener("click",function(e){let n=e.target;n.classList.contains("global-nav-track")&>mSendReport(n.text,n,"global-nav-link")}),module.exports=init;
}, {"3":3,"4":4,"17":17,"124":124,"135":135}];
window.modules["aaa-module-mounting.legacy"] = [function(require,module,exports){"use strict";const _pickBy=require(221),_each=require(406),Fingerprint2=require(408),DS=require(407),Eventify=require(246);function registerGlobals(){window.DS=DS,window.Eventify=Eventify,window.Fingerprint2=Fingerprint2,DS.value("Eventify",Eventify),DS.value("Fingerprint2",Fingerprint2),DS.value("$document",window.document),DS.value("$window",window)}function mountDollarSliceComponents(){DS.service("components",["$document","$module",function(e,n){var o=_pickBy(n.definitions,e=>e.providerStrategy===n.providers.controller),r=Object.keys(o);function t(e){return o=>{try{n.get(e,o)}catch(e){logMountError(o,e)}}}_each(r,n=>{var o=e.querySelectorAll('[data-uri*="/_components/'+n+'/"]'),r=e.querySelectorAll('[data-uri$="/_components/'+n+'"]');_each(o,t(n)),_each(r,t(n))}),this.components=r}]),DS.get("components")}function logMountError(e,n){const o=e.outerHTML.slice(0,e.outerHTML.indexOf(e.innerHTML));console.error("Error attaching controller to "+o,n)}registerGlobals(),"loading"===document.readyState?document.addEventListener("DOMContentLoaded",()=>{mountDollarSliceComponents()}):mountDollarSliceComponents();
}, {"221":221,"246":246,"406":406,"407":407,"408":408}];
window.modules["ads.legacy"] = [function(require,module,exports){"use strict";const _map=require(118),_forEach=require(107),_isString=require(268),_intersectionWith=require(409),_isEqual=require(274),_each=require(406),_debounce=require(182),_sortBy=require(205),page=require(124),visit=require(114);DS.service("adService",["Eventify","$cid","$document","$window",function(e,t,a,i){var o,n,s,r,d,c,u,l,g={},p=this,h=[],f=visit.getQueryParamsObject(["utm_campaign"]),m=document.querySelector('script[data-type="ad-a9"]'),b=[],w=!1,v=[],y=document.querySelector('script[data-name="ad-doubleverify"]');document.querySelector('script[data-name="concert-ads"]')||(i.NYM={},i.NYM.analytics={},i.NYM.analytics.adStartTime=i.performance.now(),i.googletag=i.googletag||{},i.googletag.cmd=i.googletag.cmd||[],u=i.googletag,(m||y)&&(i.googletag.cmd=i.googletag.cmd||[],i.googletag.cmd.push(function(){i.googletag.pubads().disableInitialLoad()})),m&&(l=i.setInterval(function(){void 0!==window.apstag&&void 0!==window.apstag.timeout&&(i.clearInterval(l),window.apstag.cleared=!0,l=null)},10),setTimeout(function(){l&&(i.clearInterval(l),i.googletag.pubads().refresh(),window.apstag||console.log("MESSAGE: Timeout for A9 load exceeded, aborting"))},500)),y&&(b.push(new Promise(function(e){w?e():v.push(e)})),c=i.setTimeout(T,2500)),o=function(e){var t,a,o=e.data,n=[];return o.loaded?e:(o.loaded=!0,t=null,(t=o.sizes?u.defineSlot(o.name,o.sizes,o.id).addService(u.pubads()):u.defineOutOfPageSlot(o.name,o.id).addService(u.pubads())).setTargeting("adid",o.id),f.hasOwnProperty("utm_campaign")&&t.setTargeting("utmcamp",f.utm_campaign),a=p.getAdCount(o.label),t.setTargeting("label",o.label+"_"+o.site+"-"+a),u.display(o.id),u.pubads().addEventListener("slotOnload",function(){i.NYM.analytics.firstAdLoadTime||(i.NYM.analytics.firstAdLoadTime=i.performance.now(),i.NYM.analytics.firstAdLoadLabel=e.data.label)}),n=_(o),Promise.all(b).then(function(){n?window.apstag&&window.apstag.cleared?window.apstag.fetchBids({slots:[n],timeout:window.apstag.timeout},function(){u.cmd.push(function(){window.apstag.setDisplayBids(),u.pubads().refresh([t],{changeCorrelator:!1})})}):y&&u.pubads().refresh([t],{changeCorrelator:!1}):u.pubads().refresh([t],{changeCorrelator:!1})}),e.slot=t,e)},n=function(e){var a,i,o,n=t(),s=e.getAttribute("data-name"),r=e.getAttribute("data-sizes"),d=e.getAttribute("data-label"),c=e.getAttribute("data-site");n=e.id,r&&r.length?(r=r.split(","),a=[],_map(r,function(e){e=e.split("x"),i=parseInt(e[0]),o=parseInt(e[1]),a.push([i,o])})):(e.classList.add("oop"),a=!1),this.data={id:n,name:s,sizes:a,loaded:!1,label:d,site:c},g[n]=this},r=function(e){u.cmd.push(function(){var t=o(e);g[e.data.id]=t})},s=function(e){var t=[];e.slot?(t=_(e))&&window.apstag&&window.apstag.cleared&&window.apstag.fetchBids({slots:[t],timeout:window.apstag.timeout},function(){u.cmd.push(function(){window.apstag.setDisplayBids(),u.pubads().refresh([e.slot],{changeCorrelator:!1})})}):e&&r(e)},u.cmd.push(function(){var e,t,o,n=page.getMeta("article:tag"),s=page.getMeta("author"),r=i.location.href,d=(e=a.head.querySelector(".head-gtm"),t=a.body.querySelector(".gtm"),e&&"top"===e.getAttribute("data-gtm")?"gtmtop":t&&"bottom"===t.getAttribute("data-gtm")?"gtmbottom":"");o=[],_forEach([n,s,d],function(e){_forEach(e.split(","),function(e){(e=e.trim().toLowerCase().replace(/\s/g,"-").replace(/\'|\’/g,"")).length&&o.push(e)})}),u.pubads().setTargeting("kw",o),u.pubads().setTargeting("entry_group",o),r=r.slice(r.lastIndexOf("/")+1),u.pubads().setTargeting("pn",r),u.companionAds().setRefreshUnfilledSlots(!0),u.pubads().enableAsyncRendering(),u.enableServices()}),this.load=r,this.create=function(e){return new n(e)},this.refresh=function(e){var t;_isString(e)?(t=this.getById(e),s(t)):s(e)},this.remove=function(e){var t=e.data.id;a.getElementById(t).innerHTML=""},this.getAdCount=function(e){var t,a=0,i=Object.keys(g);return _each(i,function(i){(t=g[i]).data.loaded&&t.data.label===e&&a++}),a},this.getById=function(e){return g[e]},d=_debounce(function(){var e={TopLeaderboard:1,RightColTopMPU:2,outOfPage:99,"homepageTakeover/TopLeaderboard":1},t=_sortBy(h,function(t){return e[t.data.label]||10});_forEach(t,function(e){return e.data.sizes?r(e):i.setTimeout(function(){r(e)},2e3)}),y&&window.PQ.cmd.push(()=>{try{window.PQ.loadSignals(["ids","bsc","vlp"],T)}catch(e){T(),console.error(`There has been an error loading Double Verify signals: ${e}`)}}),h=[]},10),this.addToPageLoadQueue=function(e){h.push(e),d()});function _(e){var t,a=e.sizes;return a=_intersectionWith(a,[[970,250],[970,90],[728,90],[300,600],[300,250],[320,100],[320,50]],_isEqual),e.sizes&&e.sizes.length&&(t={slotID:e.id,sizes:a,slotName:e.label}),t}function T(){i.clearTimeout(c),w=!0,_forEach(v,function(e){e()})}}]);
}, {"107":107,"114":114,"118":118,"124":124,"182":182,"205":205,"268":268,"274":274,"406":406,"409":409}];
window.modules["cid.legacy"] = [function(require,module,exports){"use strict";DS.service("$cid",function(){var r=Math.floor(100*Math.random());return function(){return"cid-"+ ++r}});
}, {}];
window.modules["client.legacy"] = [function(require,module,exports){"use strict";require("cid.legacy"),require("ads.legacy"),require("facebook.legacy"),require("aaa-module-mounting.legacy");
}, {"cid.legacy":"cid.legacy","ads.legacy":"ads.legacy","facebook.legacy":"facebook.legacy","aaa-module-mounting.legacy":"aaa-module-mounting.legacy"}];
window.modules["facebook.legacy"] = [function(require,module,exports){"use strict";DS.service("facebook",[function(){this.fb=function(i){window.FB&&window.FB[i].apply(this,Array.prototype.slice.call(arguments,1))}}]);
}, {}];
require=(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o typeof key === 'string' && key.match(/\.legacy$/)).forEach(key => window.require(key));
}
function tryToMount(fn, el, name) {
try {
fn(el); // init the controller
} catch (e) {
const elementTag = el.outerHTML.slice(0, el.outerHTML.indexOf(el.innerHTML));
console.error(`Error initializing controller for "${name}" on "${elementTag}"`, e);
}
}
/**
* mount client.js component controllers
*/
function mountComponentModules() {
Object.keys(window.modules).filter(key => typeof key === 'string' && key.match(/\.client$/)).forEach(key => {
let controllerFn = window.require(key);
if (typeof controllerFn === 'function') {
const name = key.replace('.client', ''),
instancesSelector = `[data-uri*="_components/${name}/"]`,
defaultSelector = `[data-uri$="_components${name}"]`,
instances = document.querySelectorAll(instancesSelector),
defaults = document.querySelectorAll(defaultSelector);
for (let el of instances) {
tryToMount(controllerFn, el, name);
}
for (let el of defaults) {
tryToMount(controllerFn, el, name);
}
}
});
}
// Make sure that a `window.process.env.NODE_ENV` is available in the client for any dependencies,
// services, or components that could require it
// note: the `` value is swapped for the actual environment variable in /lib/cmd/compile/scripts.js
window.process = window.process || {};
window.process.env = window.process.env || {};
if (!window.process.env.NODE_ENV) {
window.process.env.NODE_ENV = '';
}
// note: legacy controllers that require legacy services (e.g. dollar-slice) must
// wait for DOMContentLoaded to initialize themselves, as the files themselves must be mounted first
mountLegacyServices();
mountComponentModules();
// ]]